2015-03-24 23:57:23 -04:00
package client
import (
"encoding/json"
"fmt"
"net/url"
2015-03-28 12:39:24 -04:00
"github.com/docker/docker/api/types"
2015-05-05 00:18:28 -04:00
Cli "github.com/docker/docker/cli"
2015-03-24 23:57:23 -04:00
"github.com/docker/docker/opts"
flag "github.com/docker/docker/pkg/mflag"
"github.com/docker/docker/pkg/parsers"
"github.com/docker/docker/registry"
"github.com/docker/docker/runconfig"
)
2015-03-25 19:26:28 -04:00
// CmdCommit creates a new image from a container's changes.
2015-03-25 13:34:41 -04:00
//
2015-03-25 19:26:28 -04:00
// Usage: docker commit [OPTIONS] CONTAINER [REPOSITORY[:TAG]]
2015-03-24 23:57:23 -04:00
func ( cli * DockerCli ) CmdCommit ( args ... string ) error {
2015-10-08 08:46:21 -04:00
cmd := Cli . Subcmd ( "commit" , [ ] string { "CONTAINER [REPOSITORY[:TAG]]" } , Cli . DockerCommands [ "commit" ] . Description , true )
2015-03-24 23:57:23 -04:00
flPause := cmd . Bool ( [ ] string { "p" , "-pause" } , true , "Pause container during commit" )
flComment := cmd . String ( [ ] string { "m" , "-message" } , "" , "Commit message" )
flAuthor := cmd . String ( [ ] string { "a" , "#author" , "-author" } , "" , "Author (e.g., \"John Hannibal Smith <hannibal@a-team.com>\")" )
flChanges := opts . NewListOpts ( nil )
cmd . Var ( & flChanges , [ ] string { "c" , "-change" } , "Apply Dockerfile instruction to the created image" )
// FIXME: --run is deprecated, it will be replaced with inline Dockerfile commands.
flConfig := cmd . String ( [ ] string { "#run" , "#-run" } , "" , "This option is deprecated and will be removed in a future version in favor of inline Dockerfile-compatible commands" )
cmd . Require ( flag . Max , 2 )
cmd . Require ( flag . Min , 1 )
2015-07-03 05:26:09 -04:00
2015-03-28 21:22:46 -04:00
cmd . ParseFlags ( args , true )
2015-03-24 23:57:23 -04:00
var (
name = cmd . Arg ( 0 )
repository , tag = parsers . ParseRepositoryTag ( cmd . Arg ( 1 ) )
)
//Check if the given image name can be resolved
if repository != "" {
if err := registry . ValidateRepositoryName ( repository ) ; err != nil {
return err
}
}
v := url . Values { }
v . Set ( "container" , name )
v . Set ( "repo" , repository )
v . Set ( "tag" , tag )
v . Set ( "comment" , * flComment )
v . Set ( "author" , * flAuthor )
for _ , change := range flChanges . GetAll ( ) {
v . Add ( "changes" , change )
}
if * flPause != true {
v . Set ( "pause" , "0" )
}
var (
2015-03-28 12:39:24 -04:00
config * runconfig . Config
response types . ContainerCommitResponse
2015-03-24 23:57:23 -04:00
)
2015-03-28 12:39:24 -04:00
2015-03-24 23:57:23 -04:00
if * flConfig != "" {
config = & runconfig . Config { }
if err := json . Unmarshal ( [ ] byte ( * flConfig ) , config ) ; err != nil {
return err
}
}
2015-07-09 22:05:50 -04:00
serverResp , err := cli . call ( "POST" , "/commit?" + v . Encode ( ) , config , nil )
2015-03-24 23:57:23 -04:00
if err != nil {
return err
}
2015-03-28 12:39:24 -04:00
2015-07-09 22:05:50 -04:00
defer serverResp . body . Close ( )
2015-07-03 02:19:23 -04:00
2015-07-09 22:05:50 -04:00
if err := json . NewDecoder ( serverResp . body ) . Decode ( & response ) ; err != nil {
2015-03-24 23:57:23 -04:00
return err
}
2015-03-28 12:39:24 -04:00
fmt . Fprintln ( cli . out , response . ID )
2015-03-24 23:57:23 -04:00
return nil
}