diff --git a/go.mod b/go.mod index 336c2286..911b4bbf 100644 --- a/go.mod +++ b/go.mod @@ -5,6 +5,7 @@ go 1.20 require ( github.com/go-ldap/ldap/v3 v3.4.6 github.com/notaryproject/notation-core-go v1.0.2 + github.com/notaryproject/notation-plugin-framework-go v1.0.0 github.com/opencontainers/go-digest v1.0.0 github.com/opencontainers/image-spec v1.1.0-rc6 github.com/veraison/go-cose v1.1.0 diff --git a/go.sum b/go.sum index 7079c839..de10023e 100644 --- a/go.sum +++ b/go.sum @@ -17,6 +17,8 @@ github.com/google/uuid v1.3.1 h1:KjJaJ9iWZ3jOFZIf1Lqf4laDRCasjl0BCmnEGxkdLb4= github.com/google/uuid v1.3.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/notaryproject/notation-core-go v1.0.2 h1:VEt+mbsgdANd9b4jqgmx2C7U0DmwynOuD2Nhxh3bANw= github.com/notaryproject/notation-core-go v1.0.2/go.mod h1:2HkQzUwg08B3x9oVIztHsEh7Vil2Rj+tYgxH+JObLX4= +github.com/notaryproject/notation-plugin-framework-go v1.0.0 h1:6Qzr7DGXoCgXEQN+1gTZWuJAZvxh3p8Lryjn5FaLzi4= +github.com/notaryproject/notation-plugin-framework-go v1.0.0/go.mod h1:RqWSrTOtEASCrGOEffq0n8pSg2KOgKYiWqFWczRSics= github.com/opencontainers/go-digest v1.0.0 h1:apOUWs51W5PlhuyGyz9FCeeBIOUDA/6nW8Oi/yOhh5U= github.com/opencontainers/go-digest v1.0.0/go.mod h1:0JzlMkj0TRzQZfJkVvzbP0HBR3IKzErnv2BNG4W4MAM= github.com/opencontainers/image-spec v1.1.0-rc6 h1:XDqvyKsJEbRtATzkgItUqBA7QHk58yxX1Ov9HERHNqU= diff --git a/internal/mock/mocks.go b/internal/mock/mocks.go index 596be9dd..bc07c51f 100644 --- a/internal/mock/mocks.go +++ b/internal/mock/mocks.go @@ -18,8 +18,7 @@ import ( _ "embed" "github.com/notaryproject/notation-core-go/signature" - "github.com/notaryproject/notation-go/plugin" - "github.com/notaryproject/notation-go/plugin/proto" + "github.com/notaryproject/notation-plugin-framework-go/plugin" "github.com/opencontainers/go-digest" ocispec "github.com/opencontainers/image-spec/specs-go/v1" ) @@ -168,36 +167,36 @@ func (t Repository) PushSignature(ctx context.Context, mediaType string, blob [] } type PluginMock struct { - Metadata proto.GetMetadataResponse + Metadata plugin.GetMetadataResponse ExecuteResponse interface{} ExecuteError error } -func (p *PluginMock) GetMetadata(ctx context.Context, req *proto.GetMetadataRequest) (*proto.GetMetadataResponse, error) { +func (p *PluginMock) GetMetadata(ctx context.Context, req *plugin.GetMetadataRequest) (*plugin.GetMetadataResponse, error) { return &p.Metadata, nil } -func (p *PluginMock) VerifySignature(ctx context.Context, req *proto.VerifySignatureRequest) (*proto.VerifySignatureResponse, error) { - if resp, ok := p.ExecuteResponse.(*proto.VerifySignatureResponse); ok { +func (p *PluginMock) VerifySignature(ctx context.Context, req *plugin.VerifySignatureRequest) (*plugin.VerifySignatureResponse, error) { + if resp, ok := p.ExecuteResponse.(*plugin.VerifySignatureResponse); ok { return resp, nil } return nil, p.ExecuteError } -func (p *PluginMock) DescribeKey(ctx context.Context, req *proto.DescribeKeyRequest) (*proto.DescribeKeyResponse, error) { +func (p *PluginMock) DescribeKey(ctx context.Context, req *plugin.DescribeKeyRequest) (*plugin.DescribeKeyResponse, error) { panic("not implemented") // TODO: Implement } -func (p *PluginMock) GenerateSignature(ctx context.Context, req *proto.GenerateSignatureRequest) (*proto.GenerateSignatureResponse, error) { +func (p *PluginMock) GenerateSignature(ctx context.Context, req *plugin.GenerateSignatureRequest) (*plugin.GenerateSignatureResponse, error) { panic("not implemented") // TODO: Implement } -func (p *PluginMock) GenerateEnvelope(ctx context.Context, req *proto.GenerateEnvelopeRequest) (*proto.GenerateEnvelopeResponse, error) { +func (p *PluginMock) GenerateEnvelope(ctx context.Context, req *plugin.GenerateEnvelopeRequest) (*plugin.GenerateEnvelopeResponse, error) { panic("not implemented") // TODO: Implement } type PluginManager struct { - PluginCapabilities []proto.Capability + PluginCapabilities []plugin.Capability GetPluginError error PluginRunnerLoadError error PluginRunnerExecuteResponse interface{} @@ -206,7 +205,7 @@ type PluginManager struct { func (pm PluginManager) Get(ctx context.Context, name string) (plugin.Plugin, error) { return &PluginMock{ - Metadata: proto.GetMetadataResponse{ + Metadata: plugin.GetMetadataResponse{ Name: "plugin-name", Description: "for mocking in unit tests", Version: "1.0.0", diff --git a/plugin/integration_test.go b/plugin/integration_test.go index d48ad8e2..1ca78014 100644 --- a/plugin/integration_test.go +++ b/plugin/integration_test.go @@ -23,16 +23,16 @@ import ( "testing" "github.com/notaryproject/notation-go/dir" - "github.com/notaryproject/notation-go/plugin/proto" + "github.com/notaryproject/notation-plugin-framework-go/plugin" ) -var exampleMetadata = proto.GetMetadataResponse{ +var exampleMetadata = plugin.GetMetadataResponse{ Name: "foo", Description: "friendly", Version: "1", URL: "example.com", SupportedContractVersions: []string{"1.0"}, - Capabilities: []proto.Capability{"cap"}} + Capabilities: []plugin.Capability{"cap"}} func preparePlugin(t *testing.T) string { root := t.TempDir() @@ -87,11 +87,11 @@ func TestIntegration(t *testing.T) { } // validate and create - plugin, err := mgr.Get(context.Background(), "foo") + pl, err := mgr.Get(context.Background(), "foo") if err != nil { t.Fatal(err) } - metadata, err := plugin.GetMetadata(context.Background(), &proto.GetMetadataRequest{}) + metadata, err := pl.GetMetadata(context.Background(), &plugin.GetMetadataRequest{}) if err != nil { t.Fatal(err) } diff --git a/plugin/manager.go b/plugin/manager.go index 67a24395..e332dd84 100644 --- a/plugin/manager.go +++ b/plugin/manager.go @@ -26,12 +26,12 @@ import ( "github.com/notaryproject/notation-go/internal/file" "github.com/notaryproject/notation-go/internal/semver" "github.com/notaryproject/notation-go/log" - "github.com/notaryproject/notation-go/plugin/proto" + "github.com/notaryproject/notation-plugin-framework-go/plugin" ) // Manager manages plugins installed on the system. type Manager interface { - Get(ctx context.Context, name string) (Plugin, error) + Get(ctx context.Context, name string) (plugin.Plugin, error) List(ctx context.Context) ([]string, error) } @@ -48,7 +48,7 @@ func NewCLIManager(pluginFS dir.SysFS) *CLIManager { // Get returns a plugin on the system by its name. // // If the plugin is not found, the error is of type os.ErrNotExist. -func (m *CLIManager) Get(ctx context.Context, name string) (Plugin, error) { +func (m *CLIManager) Get(ctx context.Context, name string) (plugin.Plugin, error) { pluginPath := path.Join(name, binName(name)) path, err := m.pluginFS.SysPath(pluginPath) if err != nil { @@ -118,7 +118,7 @@ type CLIInstallOptions struct { // // If overwrite is set, version check is skipped. If existing // plugin is malfunctioning, it will be overwritten. -func (m *CLIManager) Install(ctx context.Context, installOpts CLIInstallOptions) (*proto.GetMetadataResponse, *proto.GetMetadataResponse, error) { +func (m *CLIManager) Install(ctx context.Context, installOpts CLIInstallOptions) (*plugin.GetMetadataResponse, *plugin.GetMetadataResponse, error) { // initialization logger := log.GetLogger(ctx) overwrite := installOpts.Overwrite @@ -153,12 +153,12 @@ func (m *CLIManager) Install(ctx context.Context, installOpts CLIInstallOptions) if err != nil { return nil, nil, err } - newPluginMetadata, err := newPlugin.GetMetadata(ctx, &proto.GetMetadataRequest{}) + newPluginMetadata, err := newPlugin.GetMetadata(ctx, &plugin.GetMetadataRequest{}) if err != nil { return nil, nil, fmt.Errorf("failed to get metadata of new plugin: %w", err) } // check plugin existence and get existing plugin metadata - var existingPluginMetadata *proto.GetMetadataResponse + var existingPluginMetadata *plugin.GetMetadataResponse existingPlugin, err := m.Get(ctx, pluginName) if err != nil { // fail only if overwrite is not set @@ -166,7 +166,7 @@ func (m *CLIManager) Install(ctx context.Context, installOpts CLIInstallOptions) return nil, nil, fmt.Errorf("failed to check plugin existence: %w", err) } } else { // plugin already exists - existingPluginMetadata, err = existingPlugin.GetMetadata(ctx, &proto.GetMetadataRequest{}) + existingPluginMetadata, err = existingPlugin.GetMetadata(ctx, &plugin.GetMetadataRequest{}) if err != nil && !overwrite { // fail only if overwrite is not set return nil, nil, fmt.Errorf("failed to get metadata of existing plugin: %w", err) } diff --git a/plugin/manager_unix.go b/plugin/manager_unix.go index 579926d3..1bde0174 100644 --- a/plugin/manager_unix.go +++ b/plugin/manager_unix.go @@ -21,11 +21,11 @@ import ( "os" "strings" - "github.com/notaryproject/notation-go/plugin/proto" + "github.com/notaryproject/notation-plugin-framework-go/plugin" ) func binName(name string) string { - return proto.Prefix + name + return plugin.BinaryPrefix + name } // isExecutableFile checks if a file at filePath is user executable @@ -44,7 +44,7 @@ func isExecutableFile(filePath string) (bool, error) { // parsePluginName checks if fileName is a valid plugin file name // and gets plugin name from it based on spec: https://github.com/notaryproject/specifications/blob/main/specs/plugin-extensibility.md#installation func parsePluginName(fileName string) (string, error) { - pluginName, found := strings.CutPrefix(fileName, proto.Prefix) + pluginName, found := strings.CutPrefix(fileName, plugin.BinaryPrefix) if !found || pluginName == "" { return "", fmt.Errorf("invalid plugin executable file name. Plugin file name requires format notation-{plugin-name}, but got %s", fileName) } diff --git a/plugin/manager_windows.go b/plugin/manager_windows.go index 26d3e11f..26c9f02f 100644 --- a/plugin/manager_windows.go +++ b/plugin/manager_windows.go @@ -20,11 +20,11 @@ import ( "strings" "github.com/notaryproject/notation-go/internal/file" - "github.com/notaryproject/notation-go/plugin/proto" + "github.com/notaryproject/notation-plugin-framework-go/plugin" ) func binName(name string) string { - return proto.Prefix + name + ".exe" + return plugin.BinaryPrefix + name + ".exe" } // isExecutableFile checks if a file at filePath is executable @@ -46,7 +46,7 @@ func parsePluginName(fileName string) (string, error) { return "", fmt.Errorf("invalid plugin executable file name. Plugin file name requires format notation-{plugin-name}.exe, but got %s", fileName) } fname := file.TrimFileExtension(fileName) - pluginName, found := strings.CutPrefix(fname, proto.Prefix) + pluginName, found := strings.CutPrefix(fname, plugin.BinaryPrefix) if !found || pluginName == "" { return "", fmt.Errorf("invalid plugin executable file name. Plugin file name requires format notation-{plugin-name}.exe, but got %s", fileName) } diff --git a/plugin/plugin.go b/plugin/plugin.go index 94befe84..c14aee19 100644 --- a/plugin/plugin.go +++ b/plugin/plugin.go @@ -11,7 +11,7 @@ // See the License for the specific language governing permissions and // limitations under the License. -// Package plugin provides the toolings to use the notation plugin. +// Package plugin provides the tooling to use the notation plugin. // // includes a CLIManager and a CLIPlugin implementation. package plugin @@ -30,44 +30,30 @@ import ( "github.com/notaryproject/notation-go/internal/slices" "github.com/notaryproject/notation-go/log" "github.com/notaryproject/notation-go/plugin/proto" + "github.com/notaryproject/notation-plugin-framework-go/plugin" ) var executor commander = &execCommander{} // for unit test -// GenericPlugin is the base requirement to be an plugin. -type GenericPlugin interface { - // GetMetadata returns the metadata information of the plugin. - GetMetadata(ctx context.Context, req *proto.GetMetadataRequest) (*proto.GetMetadataResponse, error) -} +// GenericPlugin is the base requirement to be a plugin. +// Deprecated: GenericPlugin exists for historical compatibility and should not be used. +// To access GenericPlugin, use the notation-plugin-framework-go's plugin.GenericPlugin type. +type GenericPlugin = plugin.GenericPlugin // SignPlugin defines the required methods to be a SignPlugin. -type SignPlugin interface { - GenericPlugin - - // DescribeKey returns the KeySpec of a key. - DescribeKey(ctx context.Context, req *proto.DescribeKeyRequest) (*proto.DescribeKeyResponse, error) - - // GenerateSignature generates the raw signature based on the request. - GenerateSignature(ctx context.Context, req *proto.GenerateSignatureRequest) (*proto.GenerateSignatureResponse, error) - - // GenerateEnvelope generates the Envelope with signature based on the - // request. - GenerateEnvelope(ctx context.Context, req *proto.GenerateEnvelopeRequest) (*proto.GenerateEnvelopeResponse, error) -} +// Deprecated: SignPlugin exists for historical compatibility and should not be used. +// To access SignPlugin, use the notation-plugin-framework-go's plugin.SignPlugin type. +type SignPlugin = plugin.SignPlugin // VerifyPlugin defines the required method to be a VerifyPlugin. -type VerifyPlugin interface { - GenericPlugin +// Deprecated: VerifyPlugin exists for historical compatibility and should not be used. +// To access VerifyPlugin, use the notation-plugin-framework-go's plugin.VerifyPlugin type. +type VerifyPlugin = plugin.VerifyPlugin - // VerifySignature validates the signature based on the request. - VerifySignature(ctx context.Context, req *proto.VerifySignatureRequest) (*proto.VerifySignatureResponse, error) -} - -// Plugin defines required methods to be an Plugin. -type Plugin interface { - SignPlugin - VerifyPlugin -} +// Plugin defines required methods to be a Plugin. +// Deprecated: Plugin exists for historical compatibility and should not be used. +// To access Plugin, use the notation-plugin-framework-go's plugin.Plugin type. +type Plugin = plugin.Plugin // CLIPlugin implements Plugin interface to CLI plugins. type CLIPlugin struct { @@ -90,16 +76,15 @@ func NewCLIPlugin(ctx context.Context, name, path string) (*CLIPlugin, error) { } // generate plugin - plugin := CLIPlugin{ + return &CLIPlugin{ name: name, path: path, - } - return &plugin, nil + }, nil } // GetMetadata returns the metadata information of the plugin. -func (p *CLIPlugin) GetMetadata(ctx context.Context, req *proto.GetMetadataRequest) (*proto.GetMetadataResponse, error) { - var metadata proto.GetMetadataResponse +func (p *CLIPlugin) GetMetadata(ctx context.Context, req *plugin.GetMetadataRequest) (*plugin.GetMetadataResponse, error) { + var metadata plugin.GetMetadataResponse err := run(ctx, p.name, p.path, req, &metadata) if err != nil { return nil, err @@ -120,12 +105,12 @@ func (p *CLIPlugin) GetMetadata(ctx context.Context, req *proto.GetMetadataReque // DescribeKey returns the KeySpec of a key. // // if ContractVersion is not set, it will be set by the function. -func (p *CLIPlugin) DescribeKey(ctx context.Context, req *proto.DescribeKeyRequest) (*proto.DescribeKeyResponse, error) { +func (p *CLIPlugin) DescribeKey(ctx context.Context, req *plugin.DescribeKeyRequest) (*plugin.DescribeKeyResponse, error) { if req.ContractVersion == "" { - req.ContractVersion = proto.ContractVersion + req.ContractVersion = plugin.ContractVersion } - var resp proto.DescribeKeyResponse + var resp plugin.DescribeKeyResponse err := run(ctx, p.name, p.path, req, &resp) return &resp, err } @@ -133,12 +118,12 @@ func (p *CLIPlugin) DescribeKey(ctx context.Context, req *proto.DescribeKeyReque // GenerateSignature generates the raw signature based on the request. // // if ContractVersion is not set, it will be set by the function. -func (p *CLIPlugin) GenerateSignature(ctx context.Context, req *proto.GenerateSignatureRequest) (*proto.GenerateSignatureResponse, error) { +func (p *CLIPlugin) GenerateSignature(ctx context.Context, req *plugin.GenerateSignatureRequest) (*plugin.GenerateSignatureResponse, error) { if req.ContractVersion == "" { - req.ContractVersion = proto.ContractVersion + req.ContractVersion = plugin.ContractVersion } - var resp proto.GenerateSignatureResponse + var resp plugin.GenerateSignatureResponse err := run(ctx, p.name, p.path, req, &resp) return &resp, err } @@ -146,12 +131,12 @@ func (p *CLIPlugin) GenerateSignature(ctx context.Context, req *proto.GenerateSi // GenerateEnvelope generates the Envelope with signature based on the request. // // if ContractVersion is not set, it will be set by the function. -func (p *CLIPlugin) GenerateEnvelope(ctx context.Context, req *proto.GenerateEnvelopeRequest) (*proto.GenerateEnvelopeResponse, error) { +func (p *CLIPlugin) GenerateEnvelope(ctx context.Context, req *plugin.GenerateEnvelopeRequest) (*plugin.GenerateEnvelopeResponse, error) { if req.ContractVersion == "" { - req.ContractVersion = proto.ContractVersion + req.ContractVersion = plugin.ContractVersion } - var resp proto.GenerateEnvelopeResponse + var resp plugin.GenerateEnvelopeResponse err := run(ctx, p.name, p.path, req, &resp) return &resp, err } @@ -159,17 +144,17 @@ func (p *CLIPlugin) GenerateEnvelope(ctx context.Context, req *proto.GenerateEnv // VerifySignature validates the signature based on the request. // // if ContractVersion is not set, it will be set by the function. -func (p *CLIPlugin) VerifySignature(ctx context.Context, req *proto.VerifySignatureRequest) (*proto.VerifySignatureResponse, error) { +func (p *CLIPlugin) VerifySignature(ctx context.Context, req *plugin.VerifySignatureRequest) (*plugin.VerifySignatureResponse, error) { if req.ContractVersion == "" { - req.ContractVersion = proto.ContractVersion + req.ContractVersion = plugin.ContractVersion } - var resp proto.VerifySignatureResponse + var resp plugin.VerifySignatureResponse err := run(ctx, p.name, p.path, req, &resp) return &resp, err } -func run(ctx context.Context, pluginName string, pluginPath string, req proto.Request, resp interface{}) error { +func run(ctx context.Context, pluginName string, pluginPath string, req plugin.Request, resp interface{}) error { logger := log.GetLogger(ctx) // serialize request @@ -219,16 +204,16 @@ func run(ctx context.Context, pluginName string, pluginPath string, req proto.Re // commander is defined for mocking purposes. type commander interface { - // Output runs the command, passing req to the its stdin. + // Output runs the command, passing req to the stdin. // It only returns an error if the binary can't be executed. // Returns stdout if err is nil, stderr if err is not nil. - Output(ctx context.Context, path string, command proto.Command, req []byte) (stdout []byte, stderr []byte, err error) + Output(ctx context.Context, path string, command plugin.Command, req []byte) (stdout []byte, stderr []byte, err error) } // execCommander implements the commander interface using exec.Command(). type execCommander struct{} -func (c execCommander) Output(ctx context.Context, name string, command proto.Command, req []byte) ([]byte, []byte, error) { +func (c execCommander) Output(ctx context.Context, name string, command plugin.Command, req []byte) ([]byte, []byte, error) { var stdout, stderr bytes.Buffer cmd := exec.CommandContext(ctx, name, string(command)) cmd.Stdin = bytes.NewReader(req) @@ -242,7 +227,7 @@ func (c execCommander) Output(ctx context.Context, name string, command proto.Co } // validate checks if the metadata is correctly populated. -func validate(metadata *proto.GetMetadataResponse) error { +func validate(metadata *plugin.GetMetadataResponse) error { if metadata.Name == "" { return errors.New("empty name") } @@ -261,10 +246,10 @@ func validate(metadata *proto.GetMetadataResponse) error { if len(metadata.SupportedContractVersions) == 0 { return errors.New("supported contract versions not specified") } - if !slices.Contains(metadata.SupportedContractVersions, proto.ContractVersion) { + if !slices.Contains(metadata.SupportedContractVersions, plugin.ContractVersion) { return fmt.Errorf( "contract version %q is not in the list of the plugin supported versions %v", - proto.ContractVersion, metadata.SupportedContractVersions, + plugin.ContractVersion, metadata.SupportedContractVersions, ) } return nil diff --git a/plugin/proto/algorithm.go b/plugin/proto/algorithm.go index bcf300b1..f0e2766b 100644 --- a/plugin/proto/algorithm.go +++ b/plugin/proto/algorithm.go @@ -18,25 +18,28 @@ import ( "fmt" "github.com/notaryproject/notation-core-go/signature" + "github.com/notaryproject/notation-plugin-framework-go/plugin" ) // KeySpec is type of the signing algorithm, including algorithm and size. -type KeySpec string +// Deprecated: KeySpec exists for historical compatibility and should not be used. +// To access KeySpec, use the notation-plugin-framework-go's plugin.KeySpec type. +type KeySpec = plugin.KeySpec // one of the following supported key spec names. // // https://github.com/notaryproject/notaryproject/blob/main/specs/signature-specification.md#algorithm-selection const ( - KeySpecRSA2048 KeySpec = "RSA-2048" - KeySpecRSA3072 KeySpec = "RSA-3072" - KeySpecRSA4096 KeySpec = "RSA-4096" - KeySpecEC256 KeySpec = "EC-256" - KeySpecEC384 KeySpec = "EC-384" - KeySpecEC521 KeySpec = "EC-521" + KeySpecRSA2048 = plugin.KeySpecRSA2048 + KeySpecRSA3072 = plugin.KeySpecRSA3072 + KeySpecRSA4096 = plugin.KeySpecRSA4096 + KeySpecEC256 = plugin.KeySpecEC256 + KeySpecEC384 = plugin.KeySpecEC384 + KeySpecEC521 = plugin.KeySpecEC521 ) // EncodeKeySpec returns the name of a keySpec according to the spec. -func EncodeKeySpec(k signature.KeySpec) (KeySpec, error) { +func EncodeKeySpec(k signature.KeySpec) (plugin.KeySpec, error) { switch k.Type { case signature.KeyTypeEC: switch k.Size { @@ -61,7 +64,7 @@ func EncodeKeySpec(k signature.KeySpec) (KeySpec, error) { } // DecodeKeySpec parses keySpec name to a signature.keySpec type. -func DecodeKeySpec(k KeySpec) (keySpec signature.KeySpec, err error) { +func DecodeKeySpec(k plugin.KeySpec) (keySpec signature.KeySpec, err error) { switch k { case KeySpecRSA2048: keySpec.Size = 2048 @@ -88,20 +91,22 @@ func DecodeKeySpec(k KeySpec) (keySpec signature.KeySpec, err error) { return } -// HashAlgorithm is the type of a hash algorithm. -type HashAlgorithm string +// HashAlgorithm is the type of hash algorithm. +// Deprecated: HashAlgorithm exists for historical compatibility and should not be used. +// To access HashAlgorithm, use the notation-plugin-framework-go's plugin.HashAlgorithm type. +type HashAlgorithm = plugin.HashAlgorithm // one of the following supported hash algorithm names. // // https://github.com/notaryproject/notaryproject/blob/main/specs/signature-specification.md#algorithm-selection const ( - HashAlgorithmSHA256 HashAlgorithm = "SHA-256" - HashAlgorithmSHA384 HashAlgorithm = "SHA-384" - HashAlgorithmSHA512 HashAlgorithm = "SHA-512" + HashAlgorithmSHA256 = plugin.HashAlgorithmSHA256 + HashAlgorithmSHA384 = plugin.HashAlgorithmSHA384 + HashAlgorithmSHA512 = plugin.HashAlgorithmSHA512 ) // HashAlgorithmFromKeySpec returns the name of hash function according to the spec. -func HashAlgorithmFromKeySpec(k signature.KeySpec) (HashAlgorithm, error) { +func HashAlgorithmFromKeySpec(k signature.KeySpec) (plugin.HashAlgorithm, error) { switch k.Type { case signature.KeyTypeEC: switch k.Size { @@ -126,23 +131,25 @@ func HashAlgorithmFromKeySpec(k signature.KeySpec) (HashAlgorithm, error) { } // SignatureAlgorithm is the type of signature algorithm -type SignatureAlgorithm string +// Deprecated: SignatureAlgorithm exists for historical compatibility and should not be used. +// To access SignatureAlgorithm, use the notation-plugin-framework-go's plugin.SignatureAlgorithm type. +type SignatureAlgorithm = plugin.SignatureAlgorithm // one of the following supported signing algorithm names. // // https://github.com/notaryproject/notaryproject/blob/main/specs/signature-specification.md#algorithm-selection const ( - SignatureAlgorithmECDSA_SHA256 SignatureAlgorithm = "ECDSA-SHA-256" - SignatureAlgorithmECDSA_SHA384 SignatureAlgorithm = "ECDSA-SHA-384" - SignatureAlgorithmECDSA_SHA512 SignatureAlgorithm = "ECDSA-SHA-512" - SignatureAlgorithmRSASSA_PSS_SHA256 SignatureAlgorithm = "RSASSA-PSS-SHA-256" - SignatureAlgorithmRSASSA_PSS_SHA384 SignatureAlgorithm = "RSASSA-PSS-SHA-384" - SignatureAlgorithmRSASSA_PSS_SHA512 SignatureAlgorithm = "RSASSA-PSS-SHA-512" + SignatureAlgorithmECDSA_SHA256 = plugin.SignatureAlgorithmECDSA_SHA256 + SignatureAlgorithmECDSA_SHA384 = plugin.SignatureAlgorithmECDSA_SHA384 + SignatureAlgorithmECDSA_SHA512 = plugin.SignatureAlgorithmECDSA_SHA512 + SignatureAlgorithmRSASSA_PSS_SHA256 = plugin.SignatureAlgorithmRSASSA_PSS_SHA256 + SignatureAlgorithmRSASSA_PSS_SHA384 = plugin.SignatureAlgorithmRSASSA_PSS_SHA384 + SignatureAlgorithmRSASSA_PSS_SHA512 = plugin.SignatureAlgorithmRSASSA_PSS_SHA512 ) // EncodeSigningAlgorithm returns the signing algorithm name of an algorithm // according to the spec. -func EncodeSigningAlgorithm(alg signature.Algorithm) (SignatureAlgorithm, error) { +func EncodeSigningAlgorithm(alg signature.Algorithm) (plugin.SignatureAlgorithm, error) { switch alg { case signature.AlgorithmES256: return SignatureAlgorithmECDSA_SHA256, nil @@ -161,7 +168,7 @@ func EncodeSigningAlgorithm(alg signature.Algorithm) (SignatureAlgorithm, error) } // DecodeSigningAlgorithm parses the signing algorithm name from a given string. -func DecodeSigningAlgorithm(raw SignatureAlgorithm) (signature.Algorithm, error) { +func DecodeSigningAlgorithm(raw plugin.SignatureAlgorithm) (signature.Algorithm, error) { switch raw { case SignatureAlgorithmECDSA_SHA256: return signature.AlgorithmES256, nil diff --git a/plugin/proto/algorithm_test.go b/plugin/proto/algorithm_test.go index d60af053..90a9673f 100644 --- a/plugin/proto/algorithm_test.go +++ b/plugin/proto/algorithm_test.go @@ -228,7 +228,7 @@ func TestDecodeKeySpec(t *testing.T) { }, { name: "Unsupported key spec", - raw: "unsuppored", + raw: "unsupported", expected: signature.KeySpec{}, expectErr: true, }, diff --git a/plugin/proto/errors.go b/plugin/proto/errors.go index 439cd845..bbbb112c 100644 --- a/plugin/proto/errors.go +++ b/plugin/proto/errors.go @@ -17,42 +17,40 @@ import ( "encoding/json" "errors" "fmt" + + "github.com/notaryproject/notation-plugin-framework-go/plugin" ) -type ErrorCode string +// Deprecated: ErrorCode exists for historical compatibility and should not be used. +// To access ErrorCode, use the notation-plugin-framework-go's plugin.ErrorCode type. +type ErrorCode = plugin.ErrorCode const ( // Any of the required request fields was empty, // or a value was malformed/invalid. - ErrorCodeValidation ErrorCode = "VALIDATION_ERROR" + ErrorCodeValidation = plugin.ErrorCodeValidation // The contract version used in the request is unsupported. - ErrorCodeUnsupportedContractVersion ErrorCode = "UNSUPPORTED_CONTRACT_VERSION" + ErrorCodeUnsupportedContractVersion = plugin.ErrorCodeUnsupportedContractVersion // Authentication/authorization error to use given key. - ErrorCodeAccessDenied ErrorCode = "ACCESS_DENIED" + ErrorCodeAccessDenied = plugin.ErrorCodeAccessDenied // The operation to generate signature timed out // and can be retried by Notation. - ErrorCodeTimeout ErrorCode = "TIMEOUT" + ErrorCodeTimeout = plugin.ErrorCodeTimeout // The operation to generate signature was throttles // and can be retried by Notation. - ErrorCodeThrottled ErrorCode = "THROTTLED" + ErrorCodeThrottled = plugin.ErrorCodeThrottled // Any general error that does not fall into any categories. - ErrorCodeGeneric ErrorCode = "ERROR" + ErrorCodeGeneric = plugin.ErrorCodeGeneric ) -type jsonErr struct { - Code ErrorCode `json:"errorCode"` - Message string `json:"errorMessage,omitempty"` - Metadata map[string]string `json:"errorMetadata,omitempty"` -} - // RequestError is the common error response for any request. type RequestError struct { - Code ErrorCode + Code plugin.ErrorCode Err error Metadata map[string]string } @@ -83,19 +81,19 @@ func (e RequestError) MarshalJSON() ([]byte, error) { if e.Err != nil { msg = e.Err.Error() } - return json.Marshal(jsonErr{e.Code, msg, e.Metadata}) + return json.Marshal(plugin.Error{ErrCode: e.Code, Message: msg, Metadata: e.Metadata}) } func (e *RequestError) UnmarshalJSON(data []byte) error { - var tmp jsonErr + var tmp plugin.Error err := json.Unmarshal(data, &tmp) if err != nil { return err } - if tmp.Code == "" && tmp.Message == "" && tmp.Metadata == nil { + if tmp.ErrCode == "" && tmp.Message == "" && tmp.Metadata == nil { return errors.New("incomplete json") } - *e = RequestError{Code: tmp.Code, Metadata: tmp.Metadata} + *e = RequestError{Code: tmp.ErrCode, Metadata: tmp.Metadata} if tmp.Message != "" { e.Err = errors.New(tmp.Message) } diff --git a/plugin/proto/metadata.go b/plugin/proto/metadata.go index 495506cb..c6830ce6 100644 --- a/plugin/proto/metadata.go +++ b/plugin/proto/metadata.go @@ -13,37 +13,14 @@ package proto -// GetMetadataRequest contains the parameters passed in a get-plugin-metadata -// request. -type GetMetadataRequest struct { - PluginConfig map[string]string `json:"pluginConfig,omitempty"` -} +import "github.com/notaryproject/notation-plugin-framework-go/plugin" -func (GetMetadataRequest) Command() Command { - return CommandGetMetadata -} +// GetMetadataRequest contains the parameters passed in a get-plugin-metadata request. +// Deprecated: GetMetadataRequest exists for historical compatibility and should not be used. +// To access GetMetadataRequest, use the notation-plugin-framework-go's plugin.GetMetadataRequest type. +type GetMetadataRequest = plugin.GetMetadataRequest // GetMetadataResponse provided by the plugin. -type GetMetadataResponse struct { - Name string `json:"name"` - Description string `json:"description"` - Version string `json:"version"` - URL string `json:"url"` - SupportedContractVersions []string `json:"supportedContractVersions"` - Capabilities []Capability `json:"capabilities"` -} - -// HasCapability return true if the metadata states that the -// capability is supported. -// Returns true if capability is empty. -func (resp *GetMetadataResponse) HasCapability(capability Capability) bool { - if capability == "" { - return true - } - for _, c := range resp.Capabilities { - if c == capability { - return true - } - } - return false -} +// Deprecated: GetMetadataResponse exists for historical compatibility and should not be used. +// To access GetMetadataResponse, use the notation-plugin-framework-go's plugin.GetMetadataResponse type. +type GetMetadataResponse = plugin.GetMetadataResponse diff --git a/plugin/proto/proto.go b/plugin/proto/proto.go index d550105e..1afbaea4 100644 --- a/plugin/proto/proto.go +++ b/plugin/proto/proto.go @@ -15,64 +15,72 @@ // and notation external plugin. package proto +import "github.com/notaryproject/notation-plugin-framework-go/plugin" + // Prefix is the prefix required on all plugin binary names. -const Prefix = "notation-" +// Deprecated: Prefix exists for historical compatibility and should not be used. +// To access Prefix, use the notation-plugin-framework-go's plugin.BinaryPrefix type. +const Prefix = plugin.BinaryPrefix // ContractVersion is the . version of the plugin contract. -const ContractVersion = "1.0" +// Deprecated: ContractVersion exists for historical compatibility and should not be used. +// To access ContractVersion, use the notation-plugin-framework-go's plugin.ContractVersion type. +const ContractVersion = plugin.ContractVersion // Command is a CLI command available in the plugin contract. -type Command string +type Command = plugin.Command // Request defines a plugin request, which is always associated to a command. -type Request interface { - Command() Command -} +// Deprecated: Request exists for historical compatibility and should not be used. +// To access Request, use the notation-plugin-framework-go's plugin.Request type. +type Request = plugin.Request const ( // CommandGetMetadata is the name of the plugin command // which must be supported by every plugin and returns the // plugin metadata. - CommandGetMetadata Command = "get-plugin-metadata" + CommandGetMetadata = plugin.CommandGetMetadata // CommandDescribeKey is the name of the plugin command // which must be supported by every plugin that has the // SIGNATURE_GENERATOR.RAW capability. - CommandDescribeKey Command = "describe-key" + CommandDescribeKey = plugin.CommandDescribeKey // CommandGenerateSignature is the name of the plugin command // which must be supported by every plugin that has the // SIGNATURE_GENERATOR.RAW capability. - CommandGenerateSignature Command = "generate-signature" + CommandGenerateSignature = plugin.CommandGenerateSignature // CommandGenerateEnvelope is the name of the plugin command // which must be supported by every plugin that has the // SIGNATURE_GENERATOR.ENVELOPE capability. - CommandGenerateEnvelope Command = "generate-envelope" + CommandGenerateEnvelope = plugin.CommandGenerateEnvelope // CommandVerifySignature is the name of the plugin command // which must be supported by every plugin that has // any SIGNATURE_VERIFIER.* capability - CommandVerifySignature Command = "verify-signature" + CommandVerifySignature = plugin.CommandVerifySignature ) // Capability is a feature available in the plugin contract. -type Capability string +// Deprecated: Capability exists for historical compatibility and should not be used. +// To access Capability, use the notation-plugin-framework-go's plugin.Capability type. +type Capability = plugin.Capability const ( // CapabilitySignatureGenerator is the name of the capability // for a plugin to support generating raw signatures. - CapabilitySignatureGenerator Capability = "SIGNATURE_GENERATOR.RAW" + CapabilitySignatureGenerator = plugin.CapabilitySignatureGenerator // CapabilityEnvelopeGenerator is the name of the capability // for a plugin to support generating envelope signatures. - CapabilityEnvelopeGenerator Capability = "SIGNATURE_GENERATOR.ENVELOPE" + CapabilityEnvelopeGenerator = plugin.CapabilityEnvelopeGenerator // CapabilityTrustedIdentityVerifier is the name of the // capability for a plugin to support verifying trusted identities. - CapabilityTrustedIdentityVerifier Capability = "SIGNATURE_VERIFIER.TRUSTED_IDENTITY" + CapabilityTrustedIdentityVerifier = plugin.CapabilityTrustedIdentityVerifier // CapabilityRevocationCheckVerifier is the name of the // capability for a plugin to support verifying revocation checks. - CapabilityRevocationCheckVerifier Capability = "SIGNATURE_VERIFIER.REVOCATION_CHECK" + CapabilityRevocationCheckVerifier = plugin.CapabilityRevocationCheckVerifier ) diff --git a/plugin/proto/sign.go b/plugin/proto/sign.go index aea6ef80..61be91a5 100644 --- a/plugin/proto/sign.go +++ b/plugin/proto/sign.go @@ -13,72 +13,36 @@ package proto -// DescribeKeyRequest contains the parameters passed in a describe-key request. -type DescribeKeyRequest struct { - ContractVersion string `json:"contractVersion"` - KeyID string `json:"keyId"` - PluginConfig map[string]string `json:"pluginConfig,omitempty"` -} +import "github.com/notaryproject/notation-plugin-framework-go/plugin" -func (DescribeKeyRequest) Command() Command { - return CommandDescribeKey -} +// DescribeKeyRequest contains the parameters passed in a describe-key request. +// Deprecated: DescribeKeyRequest exists for historical compatibility and should not be used. +// To access DescribeKeyRequest, use the notation-plugin-framework-go's plugin.DescribeKeyRequest type. +type DescribeKeyRequest = plugin.DescribeKeyRequest // DescribeKeyResponse is the response of a describe-key request. -type DescribeKeyResponse struct { - // The same key id as passed in the request. - KeyID string `json:"keyId"` - - // One of following supported key types: - // https://github.com/notaryproject/notaryproject/blob/main/specs/signature-specification.md#algorithm-selection - KeySpec KeySpec `json:"keySpec"` -} +// Deprecated: DescribeKeyResponse exists for historical compatibility and should not be used. +// To access DescribeKeyResponse, use the notation-plugin-framework-go's plugin.DescribeKeyResponse type. +type DescribeKeyResponse = plugin.DescribeKeyResponse // GenerateSignatureRequest contains the parameters passed in a // generate-signature request. -type GenerateSignatureRequest struct { - ContractVersion string `json:"contractVersion"` - KeyID string `json:"keyId"` - KeySpec KeySpec `json:"keySpec"` - Hash HashAlgorithm `json:"hashAlgorithm"` - Payload []byte `json:"payload"` - PluginConfig map[string]string `json:"pluginConfig,omitempty"` -} - -func (GenerateSignatureRequest) Command() Command { - return CommandGenerateSignature -} +// Deprecated: GenerateSignatureRequest exists for historical compatibility and should not be used. +// To access GenerateSignatureRequest, use the notation-plugin-framework-go's plugin.GenerateSignatureRequest type. +type GenerateSignatureRequest = plugin.GenerateSignatureRequest // GenerateSignatureResponse is the response of a generate-signature request. -type GenerateSignatureResponse struct { - KeyID string `json:"keyId"` - Signature []byte `json:"signature"` - SigningAlgorithm string `json:"signingAlgorithm"` - - // Ordered list of certificates starting with leaf certificate - // and ending with root certificate. - CertificateChain [][]byte `json:"certificateChain"` -} +// Deprecated: GenerateSignatureResponse exists for historical compatibility and should not be used. +// To access GenerateSignatureResponse, use the notation-plugin-framework-go's plugin.GenerateSignatureResponse type. +type GenerateSignatureResponse = plugin.GenerateSignatureResponse // GenerateEnvelopeRequest contains the parameters passed in a generate-envelope // request. -type GenerateEnvelopeRequest struct { - ContractVersion string `json:"contractVersion"` - KeyID string `json:"keyId"` - PayloadType string `json:"payloadType"` - SignatureEnvelopeType string `json:"signatureEnvelopeType"` - Payload []byte `json:"payload"` - ExpiryDurationInSeconds uint64 `json:"expiryDurationInSeconds,omitempty"` - PluginConfig map[string]string `json:"pluginConfig,omitempty"` -} - -func (GenerateEnvelopeRequest) Command() Command { - return CommandGenerateEnvelope -} +// Deprecated: GenerateEnvelopeRequest exists for historical compatibility and should not be used. +// To access GenerateEnvelopeRequest, use the notation-plugin-framework-go's plugin.GenerateEnvelopeRequest type. +type GenerateEnvelopeRequest = plugin.GenerateEnvelopeRequest // GenerateEnvelopeResponse is the response of a generate-envelope request. -type GenerateEnvelopeResponse struct { - SignatureEnvelope []byte `json:"signatureEnvelope"` - SignatureEnvelopeType string `json:"signatureEnvelopeType"` - Annotations map[string]string `json:"annotations,omitempty"` -} +// Deprecated: GenerateEnvelopeResponse exists for historical compatibility and should not be used. +// To access GenerateEnvelopeResponse, use the notation-plugin-framework-go's plugin.GenerateEnvelopeResponse type. +type GenerateEnvelopeResponse = plugin.GenerateEnvelopeResponse diff --git a/plugin/proto/verify.go b/plugin/proto/verify.go index 5cec2f7f..93881d8f 100644 --- a/plugin/proto/verify.go +++ b/plugin/proto/verify.go @@ -13,52 +13,38 @@ package proto -import "time" +import ( + "github.com/notaryproject/notation-plugin-framework-go/plugin" +) // VerifySignatureRequest contains the parameters passed in a verify-signature // request. -type VerifySignatureRequest struct { - ContractVersion string `json:"contractVersion"` - Signature Signature `json:"signature"` - TrustPolicy TrustPolicy `json:"trustPolicy"` - PluginConfig map[string]string `json:"pluginConfig,omitempty"` -} - -func (VerifySignatureRequest) Command() Command { - return CommandVerifySignature -} +// Deprecated: VerifySignatureRequest exists for historical compatibility and should not be used. +// To access VerifySignatureRequest, use the notation-plugin-framework-go's plugin.VerifySignatureRequest type. +type VerifySignatureRequest = plugin.VerifySignatureRequest // Signature represents a signature pulled from the envelope -type Signature struct { - CriticalAttributes CriticalAttributes `json:"criticalAttributes"` - UnprocessedAttributes []string `json:"unprocessedAttributes"` - CertificateChain [][]byte `json:"certificateChain"` -} +// Deprecated: Signature exists for historical compatibility and should not be used. +// To access Signature, use the notation-plugin-framework-go's plugin.Signature type. +type Signature = plugin.Signature // CriticalAttributes contains all Notary Project defined critical // attributes and their values in the signature envelope -type CriticalAttributes struct { - ContentType string `json:"contentType"` - SigningScheme string `json:"signingScheme"` - Expiry *time.Time `json:"expiry,omitempty"` - AuthenticSigningTime *time.Time `json:"authenticSigningTime,omitempty"` - ExtendedAttributes map[string]interface{} `json:"extendedAttributes,omitempty"` -} +// Deprecated: CriticalAttributes exists for historical compatibility and should not be used. +// To access CriticalAttributes, use the notation-plugin-framework-go's plugin.CriticalAttributes type. +type CriticalAttributes = plugin.CriticalAttributes // TrustPolicy represents trusted identities that sign the artifacts -type TrustPolicy struct { - TrustedIdentities []string `json:"trustedIdentities"` - SignatureVerification []Capability `json:"signatureVerification"` -} +// Deprecated: TrustPolicy exists for historical compatibility and should not be used. +// To access TrustPolicy, use the notation-plugin-framework-go's plugin.TrustPolicy type. +type TrustPolicy = plugin.TrustPolicy // VerifySignatureResponse is the response of a verify-signature request. -type VerifySignatureResponse struct { - VerificationResults map[Capability]*VerificationResult `json:"verificationResults"` - ProcessedAttributes []interface{} `json:"processedAttributes"` -} +// Deprecated: VerifySignatureResponse exists for historical compatibility and should not be used. +// To access VerifySignatureResponse, use the notation-plugin-framework-go's plugin.VerifySignatureResponse type. +type VerifySignatureResponse = plugin.VerifySignatureResponse // VerificationResult is the result of a verification performed by the plugin -type VerificationResult struct { - Success bool `json:"success"` - Reason string `json:"reason,omitempty"` -} +// Deprecated: VerificationResult exists for historical compatibility and should not be used. +// To access VerificationResult, use the notation-plugin-framework-go's plugin.VerificationResult type. +type VerificationResult = plugin.VerificationResult diff --git a/signer/plugin.go b/signer/plugin.go index b4ca5dbc..3bf14321 100644 --- a/signer/plugin.go +++ b/signer/plugin.go @@ -21,14 +21,15 @@ import ( "fmt" "time" + "oras.land/oras-go/v2/content" + "github.com/notaryproject/notation-core-go/signature" "github.com/notaryproject/notation-go" "github.com/notaryproject/notation-go/internal/envelope" "github.com/notaryproject/notation-go/log" - "github.com/notaryproject/notation-go/plugin" "github.com/notaryproject/notation-go/plugin/proto" + "github.com/notaryproject/notation-plugin-framework-go/plugin" ocispec "github.com/opencontainers/image-spec/specs-go/v1" - "oras.land/oras-go/v2/content" ) // pluginSigner signs artifacts and generates signatures. @@ -68,7 +69,7 @@ func (s *pluginSigner) PluginAnnotations() map[string]string { func (s *pluginSigner) Sign(ctx context.Context, desc ocispec.Descriptor, opts notation.SignerSignOptions) ([]byte, *signature.SignerInfo, error) { logger := log.GetLogger(ctx) logger.Debug("Invoking plugin's get-plugin-metadata command") - req := &proto.GetMetadataRequest{ + req := &plugin.GetMetadataRequest{ PluginConfig: s.mergeConfig(opts.PluginConfig), } metadata, err := s.plugin.GetMetadata(ctx, req) @@ -77,15 +78,15 @@ func (s *pluginSigner) Sign(ctx context.Context, desc ocispec.Descriptor, opts n } logger.Debugf("Using plugin %v with capabilities %v to sign artifact %v in signature media type %v", metadata.Name, metadata.Capabilities, desc.Digest, opts.SignatureMediaType) - if metadata.HasCapability(proto.CapabilitySignatureGenerator) { + if metadata.HasCapability(plugin.CapabilitySignatureGenerator) { return s.generateSignature(ctx, desc, opts, metadata) - } else if metadata.HasCapability(proto.CapabilityEnvelopeGenerator) { + } else if metadata.HasCapability(plugin.CapabilityEnvelopeGenerator) { return s.generateSignatureEnvelope(ctx, desc, opts) } return nil, nil, fmt.Errorf("plugin does not have signing capabilities") } -func (s *pluginSigner) generateSignature(ctx context.Context, desc ocispec.Descriptor, opts notation.SignerSignOptions, metadata *proto.GetMetadataResponse) ([]byte, *signature.SignerInfo, error) { +func (s *pluginSigner) generateSignature(ctx context.Context, desc ocispec.Descriptor, opts notation.SignerSignOptions, metadata *plugin.GetMetadataResponse) ([]byte, *signature.SignerInfo, error) { logger := log.GetLogger(ctx) logger.Debug("Generating signature by plugin") config := s.mergeConfig(opts.PluginConfig) @@ -127,7 +128,7 @@ func (s *pluginSigner) generateSignatureEnvelope(ctx context.Context, desc ocisp return nil, nil, fmt.Errorf("envelope payload can't be marshalled: %w", err) } // Execute plugin sign command. - req := &proto.GenerateEnvelopeRequest{ + req := &plugin.GenerateEnvelopeRequest{ KeyID: s.keyID, Payload: payloadBytes, SignatureEnvelopeType: opts.SignatureMediaType, @@ -193,8 +194,8 @@ func (s *pluginSigner) mergeConfig(config map[string]string) map[string]string { return c } -func (s *pluginSigner) describeKey(ctx context.Context, config map[string]string) (*proto.DescribeKeyResponse, error) { - req := &proto.DescribeKeyRequest{ +func (s *pluginSigner) describeKey(ctx context.Context, config map[string]string) (*plugin.DescribeKeyResponse, error) { + req := &plugin.DescribeKeyRequest{ KeyID: s.keyID, PluginConfig: config, } @@ -291,7 +292,7 @@ func (s *pluginPrimitiveSigner) Sign(payload []byte) ([]byte, []*x509.Certificat return nil, nil, err } - req := &proto.GenerateSignatureRequest{ + req := &plugin.GenerateSignatureRequest{ KeyID: s.keyID, KeySpec: keySpec, Hash: keySpecHash, diff --git a/signer/plugin_test.go b/signer/plugin_test.go index 3e0460a9..c3dd2b30 100644 --- a/signer/plugin_test.go +++ b/signer/plugin_test.go @@ -115,7 +115,7 @@ func (p *mockPlugin) GenerateSignature(ctx context.Context, req *proto.GenerateS return &proto.GenerateSignatureResponse{ KeyID: req.KeyID, Signature: invalidSignatureEnvelope, - SigningAlgorithm: string(sigAlg), + SigningAlgorithm: sigAlg, CertificateChain: certChain, }, err } diff --git a/verifier/verifier.go b/verifier/verifier.go index c340f8e9..81fe30f8 100644 --- a/verifier/verifier.go +++ b/verifier/verifier.go @@ -11,7 +11,7 @@ // See the License for the specific language governing permissions and // limitations under the License. -// Package Verifier provides an implementation of notation.Verifier interface +// Package verifier provides an implementation of notation.Verifier interface package verifier import ( @@ -25,6 +25,9 @@ import ( "strings" "time" + "golang.org/x/mod/semver" + "oras.land/oras-go/v2/content" + "github.com/notaryproject/notation-core-go/revocation" revocationresult "github.com/notaryproject/notation-core-go/revocation/result" "github.com/notaryproject/notation-core-go/signature" @@ -37,12 +40,10 @@ import ( trustpolicyInternal "github.com/notaryproject/notation-go/internal/trustpolicy" "github.com/notaryproject/notation-go/log" "github.com/notaryproject/notation-go/plugin" - "github.com/notaryproject/notation-go/plugin/proto" "github.com/notaryproject/notation-go/verifier/trustpolicy" "github.com/notaryproject/notation-go/verifier/truststore" + pluginframework "github.com/notaryproject/notation-plugin-framework-go/plugin" ocispec "github.com/opencontainers/image-spec/specs-go/v1" - "golang.org/x/mod/semver" - "oras.land/oras-go/v2/content" ) // verifier implements notation.Verifier and notation.verifySkipper @@ -199,14 +200,14 @@ func (v *verifier) processSignature(ctx context.Context, sigBlob []byte, envelop } // check if we need to verify using a plugin - var pluginCapabilities []proto.Capability + var pluginCapabilities []pluginframework.Capability verificationPluginName, err := getVerificationPlugin(&outcome.EnvelopeContent.SignerInfo) // use plugin, but getPluginName returns an error if err != nil && err != errExtendedAttributeNotExist { return err } - var installedPlugin plugin.VerifyPlugin + var installedPlugin pluginframework.VerifyPlugin if verificationPluginName != "" { logger.Debugf("Finding verification plugin %s", verificationPluginName) verificationPluginMinVersion, err := getVerificationPluginMinVersion(&outcome.EnvelopeContent.SignerInfo) @@ -224,7 +225,7 @@ func (v *verifier) processSignature(ctx context.Context, sigBlob []byte, envelop // filter the "verification" capabilities supported by the installed // plugin - metadata, err := installedPlugin.GetMetadata(ctx, &proto.GetMetadataRequest{PluginConfig: pluginConfig}) + metadata, err := installedPlugin.GetMetadata(ctx, &pluginframework.GetMetadataRequest{PluginConfig: pluginConfig}) if err != nil { return err } @@ -241,13 +242,13 @@ func (v *verifier) processSignature(ctx context.Context, sigBlob []byte, envelop } for _, capability := range metadata.Capabilities { - if capability == proto.CapabilityRevocationCheckVerifier || capability == proto.CapabilityTrustedIdentityVerifier { + if capability == pluginframework.CapabilityRevocationCheckVerifier || capability == pluginframework.CapabilityTrustedIdentityVerifier { pluginCapabilities = append(pluginCapabilities, capability) } } if len(pluginCapabilities) == 0 { - return notation.ErrorVerificationInconclusive{Msg: fmt.Sprintf("digital signature requires plugin %q with signature verification capabilities (%q and/or %q) installed", verificationPluginName, proto.CapabilityTrustedIdentityVerifier, proto.CapabilityRevocationCheckVerifier)} + return notation.ErrorVerificationInconclusive{Msg: fmt.Sprintf("digital signature requires plugin %q with signature verification capabilities (%q and/or %q) installed", verificationPluginName, pluginframework.CapabilityTrustedIdentityVerifier, pluginframework.CapabilityRevocationCheckVerifier)} } } @@ -262,7 +263,7 @@ func (v *verifier) processSignature(ctx context.Context, sigBlob []byte, envelop // verify x509 trusted identity based authenticity (only if notation needs // to perform this verification rather than a plugin) - if !slices.Contains(pluginCapabilities, proto.CapabilityTrustedIdentityVerifier) { + if !slices.Contains(pluginCapabilities, pluginframework.CapabilityTrustedIdentityVerifier) { logger.Debug("Validating trust identity") err = verifyX509TrustedIdentities(outcome.EnvelopeContent.SignerInfo.CertificateChain, trustPolicy) if err != nil { @@ -296,7 +297,7 @@ func (v *verifier) processSignature(ctx context.Context, sigBlob []byte, envelop // check if we need to bypass the revocation check, since revocation can be // skipped using a trust policy or a plugin may override the check if outcome.VerificationLevel.Enforcement[trustpolicy.TypeRevocation] != trustpolicy.ActionSkip && - !slices.Contains(pluginCapabilities, proto.CapabilityRevocationCheckVerifier) { + !slices.Contains(pluginCapabilities, pluginframework.CapabilityRevocationCheckVerifier) { logger.Debug("Validating revocation") revocationResult := verifyRevocation(outcome, v.revocationClient, logger) @@ -309,11 +310,11 @@ func (v *verifier) processSignature(ctx context.Context, sigBlob []byte, envelop // perform extended verification using verification plugin if present if installedPlugin != nil { - var capabilitiesToVerify []proto.Capability + var capabilitiesToVerify []pluginframework.Capability for _, pc := range pluginCapabilities { // skip the revocation capability if the trust policy is configured // to skip it - if outcome.VerificationLevel.Enforcement[trustpolicy.TypeRevocation] == trustpolicy.ActionSkip && pc == proto.CapabilityRevocationCheckVerifier { + if outcome.VerificationLevel.Enforcement[trustpolicy.TypeRevocation] == trustpolicy.ActionSkip && pc == pluginframework.CapabilityRevocationCheckVerifier { logger.Debugf("Skipping the %v validation", pc) continue } @@ -333,7 +334,7 @@ func (v *verifier) processSignature(ctx context.Context, sigBlob []byte, envelop return nil } -func processPluginResponse(logger log.Logger, capabilitiesToVerify []proto.Capability, response *proto.VerifySignatureResponse, outcome *notation.VerificationOutcome) error { +func processPluginResponse(logger log.Logger, capabilitiesToVerify []pluginframework.Capability, response *pluginframework.VerifySignatureResponse, outcome *notation.VerificationOutcome) error { verificationPluginName, err := getVerificationPlugin(&outcome.EnvelopeContent.SignerInfo) if err != nil { return err @@ -353,7 +354,7 @@ func processPluginResponse(logger log.Logger, capabilitiesToVerify []proto.Capab return notation.ErrorVerificationInconclusive{Msg: fmt.Sprintf("verification plugin %q failed to verify %q", verificationPluginName, capability)} } switch capability { - case proto.CapabilityTrustedIdentityVerifier: + case pluginframework.CapabilityTrustedIdentityVerifier: if !pluginResult.Success { // find the Authenticity VerificationResult that we already // created during x509 trust store verification @@ -371,7 +372,7 @@ func processPluginResponse(logger log.Logger, capabilitiesToVerify []proto.Capab return authenticityResult.Error } } - case proto.CapabilityRevocationCheckVerifier: + case pluginframework.CapabilityRevocationCheckVerifier: var revocationResult *notation.ValidationResult if !pluginResult.Success { revocationResult = ¬ation.ValidationResult{ @@ -634,7 +635,7 @@ func verifyRevocation(outcome *notation.VerificationOutcome, r revocation.Revoca return result } -func executePlugin(ctx context.Context, installedPlugin plugin.VerifyPlugin, trustPolicy *trustpolicy.TrustPolicy, capabilitiesToVerify []proto.Capability, envelopeContent *signature.EnvelopeContent, pluginConfig map[string]string) (*proto.VerifySignatureResponse, error) { +func executePlugin(ctx context.Context, installedPlugin pluginframework.VerifyPlugin, trustPolicy *trustpolicy.TrustPolicy, capabilitiesToVerify []pluginframework.Capability, envelopeContent *signature.EnvelopeContent, pluginConfig map[string]string) (*pluginframework.VerifySignatureResponse, error) { logger := log.GetLogger(ctx) // sanity check if installedPlugin == nil { @@ -662,8 +663,8 @@ func executePlugin(ctx context.Context, installedPlugin plugin.VerifyPlugin, tru // https://github.com/notaryproject/notation-core-go/issues/38 } - signature := proto.Signature{ - CriticalAttributes: proto.CriticalAttributes{ + signature := pluginframework.Signature{ + CriticalAttributes: pluginframework.CriticalAttributes{ ContentType: payloadInfo.ContentType, SigningScheme: string(signerInfo.SignedAttributes.SigningScheme), Expiry: &signerInfo.SignedAttributes.Expiry, @@ -674,12 +675,12 @@ func executePlugin(ctx context.Context, installedPlugin plugin.VerifyPlugin, tru CertificateChain: certChain, } - policy := proto.TrustPolicy{ + policy := pluginframework.TrustPolicy{ TrustedIdentities: trustPolicy.TrustedIdentities, SignatureVerification: capabilitiesToVerify, } - req := &proto.VerifySignatureRequest{ + req := &pluginframework.VerifySignatureRequest{ Signature: signature, TrustPolicy: policy, PluginConfig: pluginConfig,