diff --git a/runtime/v2/example/README.md b/runtime/v2/example/README.md new file mode 100644 index 000000000..19a748c68 --- /dev/null +++ b/runtime/v2/example/README.md @@ -0,0 +1,6 @@ +# Example Shim + +This directory provides skeleton code as the starting point for creating a Runtime v2 shim. +This allows runtime authors to quickly bootstrap new shim implementations. + +For full documentation on building a shim for containerd, see the [Shim Documentation](../README.md) file. diff --git a/runtime/v2/example/cmd/main.go b/runtime/v2/example/cmd/main.go new file mode 100644 index 000000000..fcef0d25b --- /dev/null +++ b/runtime/v2/example/cmd/main.go @@ -0,0 +1,29 @@ +// +build linux + +/* + Copyright The containerd Authors. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package main + +import ( + "github.com/containerd/containerd/runtime/v2/example" + "github.com/containerd/containerd/runtime/v2/shim" +) + +func main() { + // init and execute the shim + shim.Run("io.containerd.example.v1", example.New) +} diff --git a/runtime/v2/example/example.go b/runtime/v2/example/example.go new file mode 100644 index 000000000..3b5b73873 --- /dev/null +++ b/runtime/v2/example/example.go @@ -0,0 +1,141 @@ +// +build linux + +/* + Copyright The containerd Authors. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +*/ + +package example + +import ( + "context" + "os" + + "github.com/containerd/containerd/errdefs" + "github.com/containerd/containerd/events" + "github.com/containerd/containerd/runtime/v2/shim" + taskAPI "github.com/containerd/containerd/runtime/v2/task" + ptypes "github.com/gogo/protobuf/types" +) + +var ( + // check to make sure the *service implements the GRPC API + _ = (taskAPI.TaskService)(&service{}) + // common response type + empty = &ptypes.Empty{} +) + +// New returns a new shim service +func New(ctx context.Context, id string, publisher events.Publisher) (shim.Shim, error) { + return &service{}, nil +} + +type service struct { +} + +// StartShim is a binary call that executes a new shim returning the address +func (s *service) StartShim(ctx context.Context, id, containerdBinary, containerdAddress string) (string, error) { + return "", nil +} + +// Cleanup is a binary call that cleans up any resources used by the shim when the service crashes +func (s *service) Cleanup(ctx context.Context) (*taskAPI.DeleteResponse, error) { + return nil, errdefs.ErrNotImplemented +} + +// Create a new container +func (s *service) Create(ctx context.Context, r *taskAPI.CreateTaskRequest) (_ *taskAPI.CreateTaskResponse, err error) { + return nil, errdefs.ErrNotImplemented +} + +// Start the primary user process inside the container +func (s *service) Start(ctx context.Context, r *taskAPI.StartRequest) (*taskAPI.StartResponse, error) { + return nil, errdefs.ErrNotImplemented +} + +// Delete a process or container +func (s *service) Delete(ctx context.Context, r *taskAPI.DeleteRequest) (*taskAPI.DeleteResponse, error) { + return nil, errdefs.ErrNotImplemented +} + +// Exec an additional process inside the container +func (s *service) Exec(ctx context.Context, r *taskAPI.ExecProcessRequest) (*ptypes.Empty, error) { + return nil, errdefs.ErrNotImplemented +} + +// ResizePty of a process +func (s *service) ResizePty(ctx context.Context, r *taskAPI.ResizePtyRequest) (*ptypes.Empty, error) { + return nil, errdefs.ErrNotImplemented +} + +// State returns runtime state of a process +func (s *service) State(ctx context.Context, r *taskAPI.StateRequest) (*taskAPI.StateResponse, error) { + return nil, errdefs.ErrNotImplemented +} + +// Pause the container +func (s *service) Pause(ctx context.Context, r *taskAPI.PauseRequest) (*ptypes.Empty, error) { + return nil, errdefs.ErrNotImplemented +} + +// Resume the container +func (s *service) Resume(ctx context.Context, r *taskAPI.ResumeRequest) (*ptypes.Empty, error) { + return nil, errdefs.ErrNotImplemented +} + +// Kill a process +func (s *service) Kill(ctx context.Context, r *taskAPI.KillRequest) (*ptypes.Empty, error) { + return nil, errdefs.ErrNotImplemented +} + +// Pids returns all pids inside the container +func (s *service) Pids(ctx context.Context, r *taskAPI.PidsRequest) (*taskAPI.PidsResponse, error) { + return nil, errdefs.ErrNotImplemented +} + +// CloseIO of a process +func (s *service) CloseIO(ctx context.Context, r *taskAPI.CloseIORequest) (*ptypes.Empty, error) { + return nil, errdefs.ErrNotImplemented +} + +// Checkpoint the container +func (s *service) Checkpoint(ctx context.Context, r *taskAPI.CheckpointTaskRequest) (*ptypes.Empty, error) { + return nil, errdefs.ErrNotImplemented +} + +// Connect returns shim information of the underlying service +func (s *service) Connect(ctx context.Context, r *taskAPI.ConnectRequest) (*taskAPI.ConnectResponse, error) { + return nil, errdefs.ErrNotImplemented +} + +// Shutdown is called after the underlying resources of the shim are cleaned up and the service can be stopped +func (s *service) Shutdown(ctx context.Context, r *taskAPI.ShutdownRequest) (*ptypes.Empty, error) { + os.Exit(0) + return empty, nil +} + +// Stats returns container level system stats for a container and its processes +func (s *service) Stats(ctx context.Context, r *taskAPI.StatsRequest) (*taskAPI.StatsResponse, error) { + return nil, errdefs.ErrNotImplemented +} + +// Update the live container +func (s *service) Update(ctx context.Context, r *taskAPI.UpdateTaskRequest) (*ptypes.Empty, error) { + return nil, errdefs.ErrNotImplemented +} + +// Wait for a process to exit +func (s *service) Wait(ctx context.Context, r *taskAPI.WaitRequest) (*taskAPI.WaitResponse, error) { + return nil, errdefs.ErrNotImplemented +}