@@ -2,17 +2,21 @@ package docker
22
33import (
44 "context"
5- "github.com/docker/docker/api/types/network"
6-
7- "github.com/docker/docker/api/types/container"
8- "github.com/docker/docker/api/types/image"
9-
5+ "encoding/json"
6+ "fmt"
107 "github.com/1Panel-dev/1Panel/agent/app/model"
8+ "github.com/1Panel-dev/1Panel/agent/app/task"
119 "github.com/1Panel-dev/1Panel/agent/global"
12-
1310 "github.com/docker/docker/api/types"
11+ "github.com/docker/docker/api/types/container"
1412 "github.com/docker/docker/api/types/filters"
13+ "github.com/docker/docker/api/types/image"
14+ "github.com/docker/docker/api/types/network"
1515 "github.com/docker/docker/client"
16+ "io"
17+ "os"
18+ "strings"
19+ "time"
1620)
1721
1822func NewDockerClient () (* client.Client , error ) {
@@ -28,10 +32,6 @@ func NewDockerClient() (*client.Client, error) {
2832 return cli , nil
2933}
3034
31- type Client struct {
32- cli * client.Client
33- }
34-
3535func NewClient () (Client , error ) {
3636 var settingItem model.Setting
3737 _ = global .DB .Where ("key = ?" , "DockerSockPath" ).First (& settingItem ).Error
@@ -48,10 +48,8 @@ func NewClient() (Client, error) {
4848 }, nil
4949}
5050
51- func NewClientWithCli (cli * client.Client ) (Client , error ) {
52- return Client {
53- cli : cli ,
54- }, nil
51+ type Client struct {
52+ cli * client.Client
5553}
5654
5755func (c Client ) Close () {
@@ -142,6 +140,7 @@ func CreateDefaultDockerNetwork() error {
142140 global .LOG .Errorf ("init docker client error %s" , err .Error ())
143141 return err
144142 }
143+
145144 defer cli .Close ()
146145 if ! cli .NetworkExist ("1panel-network" ) {
147146 if err := cli .CreateNetwork ("1panel-network" ); err != nil {
@@ -151,3 +150,66 @@ func CreateDefaultDockerNetwork() error {
151150 }
152151 return nil
153152}
153+
154+ func setLog (id , newLastLine string , task * task.Task ) error {
155+ data , err := os .ReadFile (task .Task .LogFile )
156+ if err != nil {
157+ return fmt .Errorf ("failed to read file: %v" , err )
158+ }
159+ lines := strings .Split (string (data ), "\n " )
160+ exist := false
161+ for index , line := range lines {
162+ if strings .Contains (line , id ) {
163+ lines [index ] = newLastLine
164+ exist = true
165+ break
166+ }
167+ }
168+ if ! exist {
169+ task .Log (newLastLine )
170+ return nil
171+ }
172+ output := strings .Join (lines , "\n " )
173+ _ = os .WriteFile (task .Task .LogFile , []byte (output ), os .ModePerm )
174+ return nil
175+ }
176+
177+ func (c Client ) PullImageWithProcess (task * task.Task , imageName string ) error {
178+ out , err := c .cli .ImagePull (context .Background (), imageName , image.PullOptions {})
179+ if err != nil {
180+ return err
181+ }
182+ defer out .Close ()
183+ decoder := json .NewDecoder (out )
184+ for {
185+ var progress map [string ]interface {}
186+ if err = decoder .Decode (& progress ); err != nil {
187+ if err == io .EOF {
188+ break
189+ }
190+ return err
191+ }
192+ timeStr := time .Now ().Format ("2006/01/02 15:04:05" )
193+ status , _ := progress ["status" ].(string )
194+ if status == "Downloading" || status == "Extracting" {
195+ id , _ := progress ["id" ].(string )
196+ progressDetail , _ := progress ["progressDetail" ].(map [string ]interface {})
197+ current , _ := progressDetail ["current" ].(float64 )
198+ progressStr := ""
199+ total , ok := progressDetail ["total" ].(float64 )
200+ if ok {
201+ progressStr = fmt .Sprintf ("%s %s [%s] --- %.2f%%" , timeStr , status , id , (current / total )* 100 )
202+ } else {
203+ progressStr = fmt .Sprintf ("%s %s [%s] --- %.2f%%" , timeStr , status , id , current )
204+ }
205+
206+ _ = setLog (id , progressStr , task )
207+ }
208+ if status == "Pull complete" || status == "Download complete" {
209+ id , _ := progress ["id" ].(string )
210+ progressStr := fmt .Sprintf ("%s %s [%s] --- %.2f%%" , timeStr , status , id , 100.0 )
211+ _ = setLog (id , progressStr , task )
212+ }
213+ }
214+ return nil
215+ }
0 commit comments