@@ -11,6 +11,7 @@ import (
1111 "strings"
1212 "time"
1313
14+ "github.com/containerd/errdefs"
1415 "github.com/docker/cli/cli/command"
1516 "github.com/docker/cli/cli/context/docker"
1617 clientpkg "github.com/docker/docker/client"
@@ -131,8 +132,59 @@ func NewContextForTest(endpoint string, client DockerHttpClient) (*ModelRunnerCo
131132 }, nil
132133}
133134
135+ // wakeUpCloudIfIdle checks if the Docker Cloud context is idle and wakes it up if needed.
136+ func wakeUpCloudIfIdle (ctx context.Context , cli * command.DockerCli ) error {
137+ ctx , cancel := context .WithTimeout (ctx , 5 * time .Second )
138+ defer cancel ()
139+
140+ info , err := cli .Client ().Info (ctx )
141+ if err != nil {
142+ return fmt .Errorf ("failed to get Docker info: %w" , err )
143+ }
144+
145+ // Check if the cloud.docker.run.engine label is set to "idle".
146+ isIdle := false
147+ for _ , label := range info .Labels {
148+ if label == "cloud.docker.run.engine=idle" {
149+ isIdle = true
150+ break
151+ }
152+ }
153+ if ! isIdle {
154+ return nil
155+ }
156+
157+ // Wake up Docker Cloud by triggering an empty ContainerCreate call.
158+ dockerClient , err := DockerClientForContext (cli , cli .CurrentContext ())
159+ if err != nil {
160+ return fmt .Errorf ("failed to create Docker client: %w" , err )
161+ }
162+
163+ // The call is expected to fail with a client error due to nil arguments, but it triggers
164+ // Docker Cloud to wake up from idle. Only return unexpected failures (network issues,
165+ // server errors) so they're logged as warnings.
166+ _ , err = dockerClient .ContainerCreate (ctx , nil , nil , nil , nil , "" )
167+ if err != nil && ! errdefs .IsInvalidArgument (err ) {
168+ return fmt .Errorf ("failed to wake up Docker Cloud: %w" , err )
169+ }
170+
171+ // Verify Docker Cloud is no longer idle.
172+ info , err = cli .Client ().Info (ctx )
173+ if err != nil {
174+ return fmt .Errorf ("failed to verify Docker Cloud wake-up: %w" , err )
175+ }
176+
177+ for _ , label := range info .Labels {
178+ if label == "cloud.docker.run.engine=idle" {
179+ return fmt .Errorf ("failed to wake up Docker Cloud from idle state" )
180+ }
181+ }
182+
183+ return nil
184+ }
185+
134186// DetectContext determines the current Docker Model Runner context.
135- func DetectContext (ctx context.Context , cli * command.DockerCli ) (* ModelRunnerContext , error ) {
187+ func DetectContext (ctx context.Context , cli * command.DockerCli , printer standalone. StatusPrinter ) (* ModelRunnerContext , error ) {
136188 // Check for an explicit endpoint setting.
137189 modelRunnerHost := os .Getenv ("MODEL_RUNNER_HOST" )
138190
@@ -151,6 +203,13 @@ func DetectContext(ctx context.Context, cli *command.DockerCli) (*ModelRunnerCon
151203 }
152204 } else if isCloudContext (cli ) {
153205 kind = types .ModelRunnerEngineKindCloud
206+ // Wake up Docker Cloud if it's idle.
207+ if err := wakeUpCloudIfIdle (ctx , cli ); err != nil {
208+ // Log the error as a warning but don't fail - we'll try to use Docker Cloud anyway.
209+ // The downside is that the wrong docker/model-runner image might be automatically
210+ // pulled on docker install-runner because the runtime can't be properly verified.
211+ printer .Printf ("Warning: %v\n " , err )
212+ }
154213 }
155214
156215 // Compute the URL prefix based on the associated engine kind.
0 commit comments