@@ -158,7 +158,7 @@ func newTCPClient(ctx context.Context, endpoint string, tlsConfig *tls.Config, t
158158 return containerd .NewWithConn (conn , containerd .WithTimeout (timeout ))
159159}
160160
161- func (r * runtime ) Platform () platforms.Matcher { return r .platform }
161+ func (r * runtime ) Platform () platforms.MatchComparer { return r .platform }
162162func (r * runtime ) ContainerdClient () * containerd.Client { return r .client }
163163func (r * runtime ) Namespace () string { return r .namespace }
164164
@@ -225,6 +225,12 @@ func (r *runtime) getImage(ctx context.Context, ref string) (containerd.Image, e
225225 return containerd .NewImageWithPlatform (r .client , i , r .platform ), nil
226226}
227227
228+ func (r * runtime ) RecommendedRuntimeInfo (ctx context.Context , container * model.Container ) * containers.RuntimeInfo {
229+ cc := & containers.Container {}
230+ lo .Must0 (withRuntime (r .runcPath , container )(ctx , r .client , cc ))
231+ return & cc .Runtime
232+ }
233+
228234func (r * runtime ) CreateContainer (ctx context.Context , container * model.Container , following bool ) error {
229235 ctx = namespaces .WithNamespace (ctx , r .namespace )
230236
@@ -273,6 +279,51 @@ func (r *runtime) CreateContainer(ctx context.Context, container *model.Containe
273279 return nil
274280}
275281
282+ func (r * runtime ) UpdateContainer (ctx context.Context , container * model.Container , opts * ContainerUpdateOptions ) error {
283+ ctx = namespaces .WithNamespace (ctx , r .namespace )
284+
285+ image , err := r .getImage (ctx , container .Image )
286+ if err != nil {
287+ return fmt .Errorf ("get image %s: %w" , container .Image , err )
288+ }
289+
290+ updateOptions := []containerd.UpdateContainerOpts {
291+ containerd .UpdateContainerOpts (containerd .WithImageName (container .Image )),
292+ containerd .UpdateContainerOpts (withLogPath (container .Process .LogPath )),
293+ // containerd.UpdateContainerOpts(withRuntime(r.runcPath, container)), fixme: runtime donot support update
294+ containerd .UpdateContainerOpts (containerd .WithNewSpec (containerSpecOpts (r .namespace , image , container )... )),
295+ }
296+ if container .Process .RestartPolicy == model .RestartPolicyAlways {
297+ updateOptions = append (updateOptions , restart .WithStatus (containerd .Running ))
298+ }
299+ if opts .UpdateSnapshot {
300+ updateOptions = append (updateOptions , containerd .UpdateContainerOpts (withNewSnapshotAndConfig (image , container .ConfigContent )))
301+ }
302+
303+ c , err := r .client .LoadContainer (ctx , container .Name )
304+ if err != nil {
305+ return fmt .Errorf ("load container: %w" , err )
306+ }
307+ err = c .Update (ctx , updateOptions ... )
308+ if err != nil {
309+ return fmt .Errorf ("update container: %w" , err )
310+ }
311+
312+ task , err := c .Task (ctx , nil )
313+ if err != nil {
314+ if errdefs .IsNotFound (err ) {
315+ return nil
316+ }
317+ return fmt .Errorf ("load task: %w" , err )
318+ }
319+
320+ spec , err := c .Spec (ctx )
321+ if err != nil {
322+ return fmt .Errorf ("get container spec: %w" , err )
323+ }
324+ return task .Update (ctx , containerd .WithResources (spec .Linux .Resources ))
325+ }
326+
276327func (r * runtime ) RemoveContainer (ctx context.Context , containerID string ) error {
277328 ctx = namespaces .WithNamespace (ctx , r .namespace )
278329
@@ -354,6 +405,7 @@ func (r *runtime) GetContainerStatus(ctx context.Context, containerID string) (C
354405
355406 return ContainerStatus {
356407 Status : status ,
408+ Task : task ,
357409 Container : lo .Must (c .Info (ctx , containerd .WithoutRefreshedMetadata )),
358410 }, nil
359411}
@@ -399,6 +451,10 @@ func (r *runtime) doConfig(ctx context.Context) error {
399451 return nil
400452}
401453
454+ func ContainerSpecOpts (namespace string , img containerd.Image , container * model.Container ) []oci.SpecOpts {
455+ return containerSpecOpts (namespace , img , container )
456+ }
457+
402458func containerSpecOpts (namespace string , img containerd.Image , container * model.Container ) []oci.SpecOpts {
403459 var specOpts []oci.SpecOpts
404460 specOpts = append (specOpts , oci .WithProcessCwd (container .Process .WorkingDir ))
@@ -576,6 +632,16 @@ func withLogPath(logPath string) func(ctx context.Context, client *containerd.Cl
576632 }
577633}
578634
635+ func GetLogPath (c * containers.Container ) string {
636+ if c .Labels [restart .LogURILabel ] != "" {
637+ return strings .TrimPrefix (c .Labels [restart .LogURILabel ], "file://" )
638+ }
639+ if c .Labels [restart .LogPathLabel ] != "" {
640+ return c .Labels [restart .LogPathLabel ]
641+ }
642+ return ""
643+ }
644+
579645func withRlimits (rlimits []specs.POSIXRlimit ) oci.SpecOpts {
580646 return func (_ context.Context , _ oci.Client , _ * containers.Container , spec * oci.Spec ) error {
581647 if spec .Process == nil {
0 commit comments