mirror of
https://github.com/containers/podman.git
synced 2025-06-20 17:13:43 +08:00
Merge pull request #8696 from Luap99/podman-events-until
podman events allow future time for --until
This commit is contained in:
@ -216,8 +216,5 @@ func (e EventLogFile) getTail(options ReadOptions) (*tail.Tail, error) {
|
|||||||
reopen = false
|
reopen = false
|
||||||
}
|
}
|
||||||
stream := options.Stream
|
stream := options.Stream
|
||||||
if len(options.Until) > 0 {
|
|
||||||
stream = false
|
|
||||||
}
|
|
||||||
return tail.TailFile(e.options.LogFilePath, tail.Config{ReOpen: reopen, Follow: stream, Location: &seek, Logger: tail.DiscardingLogger, Poll: true})
|
return tail.TailFile(e.options.LogFilePath, tail.Config{ReOpen: reopen, Follow: stream, Location: &seek, Logger: tail.DiscardingLogger, Poll: true})
|
||||||
}
|
}
|
||||||
|
@ -8,6 +8,7 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
|
"github.com/containers/podman/v2/pkg/util"
|
||||||
"github.com/coreos/go-systemd/v22/journal"
|
"github.com/coreos/go-systemd/v22/journal"
|
||||||
"github.com/coreos/go-systemd/v22/sdjournal"
|
"github.com/coreos/go-systemd/v22/sdjournal"
|
||||||
"github.com/pkg/errors"
|
"github.com/pkg/errors"
|
||||||
@ -72,6 +73,13 @@ func (e EventJournalD) Read(ctx context.Context, options ReadOptions) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return errors.Wrapf(err, "failed to generate event options")
|
return errors.Wrapf(err, "failed to generate event options")
|
||||||
}
|
}
|
||||||
|
var untilTime time.Time
|
||||||
|
if len(options.Until) > 0 {
|
||||||
|
untilTime, err = util.ParseInputTime(options.Until)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
}
|
||||||
j, err := sdjournal.NewJournal()
|
j, err := sdjournal.NewJournal()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
@ -122,10 +130,14 @@ func (e EventJournalD) Read(ctx context.Context, options ReadOptions) error {
|
|||||||
return errors.Wrap(err, "failed to get journal cursor")
|
return errors.Wrap(err, "failed to get journal cursor")
|
||||||
}
|
}
|
||||||
if prevCursor == newCursor {
|
if prevCursor == newCursor {
|
||||||
if len(options.Until) > 0 || !options.Stream {
|
if !options.Stream || (len(options.Until) > 0 && time.Now().After(untilTime)) {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
_ = j.Wait(sdjournal.IndefiniteWait)
|
t := sdjournal.IndefiniteWait
|
||||||
|
if len(options.Until) > 0 {
|
||||||
|
t = time.Until(untilTime)
|
||||||
|
}
|
||||||
|
_ = j.Wait(t)
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
prevCursor = newCursor
|
prevCursor = newCursor
|
||||||
|
@ -4,7 +4,9 @@ import (
|
|||||||
"context"
|
"context"
|
||||||
"fmt"
|
"fmt"
|
||||||
"os"
|
"os"
|
||||||
|
"time"
|
||||||
|
|
||||||
|
"github.com/containers/podman/v2/pkg/util"
|
||||||
"github.com/containers/storage"
|
"github.com/containers/storage"
|
||||||
"github.com/pkg/errors"
|
"github.com/pkg/errors"
|
||||||
)
|
)
|
||||||
@ -51,6 +53,16 @@ func (e EventLogFile) Read(ctx context.Context, options ReadOptions) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
if len(options.Until) > 0 {
|
||||||
|
untilTime, err := util.ParseInputTime(options.Until)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
go func() {
|
||||||
|
time.Sleep(time.Until(untilTime))
|
||||||
|
t.Stop()
|
||||||
|
}()
|
||||||
|
}
|
||||||
funcDone := make(chan bool)
|
funcDone := make(chan bool)
|
||||||
copy := true
|
copy := true
|
||||||
go func() {
|
go func() {
|
||||||
|
@ -502,6 +502,7 @@ func WithEventsLogger(logger string) RuntimeOption {
|
|||||||
}
|
}
|
||||||
|
|
||||||
rt.config.Engine.EventsLogger = logger
|
rt.config.Engine.EventsLogger = logger
|
||||||
|
rt.config.Engine.EventsLogFilePath = filepath.Join(rt.config.Engine.TmpDir, "events", "events.log")
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
@ -110,6 +110,7 @@ func GetEvents(w http.ResponseWriter, r *http.Request) {
|
|||||||
Until: query.Until,
|
Until: query.Until,
|
||||||
}
|
}
|
||||||
errorChannel <- runtime.Events(r.Context(), readOpts)
|
errorChannel <- runtime.Events(r.Context(), readOpts)
|
||||||
|
|
||||||
}()
|
}()
|
||||||
|
|
||||||
var flush = func() {}
|
var flush = func() {}
|
||||||
@ -130,8 +131,8 @@ func GetEvents(w http.ResponseWriter, r *http.Request) {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
// FIXME StatusOK already sent above cannot send 500 here
|
// FIXME StatusOK already sent above cannot send 500 here
|
||||||
utils.InternalServerError(w, err)
|
utils.InternalServerError(w, err)
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
return
|
||||||
case evt := <-eventChannel:
|
case evt := <-eventChannel:
|
||||||
if evt == nil {
|
if evt == nil {
|
||||||
continue
|
continue
|
||||||
|
@ -5,9 +5,11 @@ import (
|
|||||||
"fmt"
|
"fmt"
|
||||||
"os"
|
"os"
|
||||||
"strings"
|
"strings"
|
||||||
|
"sync"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
. "github.com/containers/podman/v2/test/utils"
|
. "github.com/containers/podman/v2/test/utils"
|
||||||
|
"github.com/containers/storage/pkg/stringid"
|
||||||
. "github.com/onsi/ginkgo"
|
. "github.com/onsi/ginkgo"
|
||||||
. "github.com/onsi/gomega"
|
. "github.com/onsi/gomega"
|
||||||
. "github.com/onsi/gomega/gexec"
|
. "github.com/onsi/gomega/gexec"
|
||||||
@ -115,10 +117,7 @@ var _ = Describe("Podman events", func() {
|
|||||||
SkipIfNotFedora()
|
SkipIfNotFedora()
|
||||||
_, ec, _ := podmanTest.RunLsContainer("")
|
_, ec, _ := podmanTest.RunLsContainer("")
|
||||||
Expect(ec).To(Equal(0))
|
Expect(ec).To(Equal(0))
|
||||||
test := podmanTest.Podman([]string{"events", "--help"})
|
result := podmanTest.Podman([]string{"events", "--stream=false", "--until", "1h"})
|
||||||
test.WaitWithDefaultTimeout()
|
|
||||||
fmt.Println(test.OutputToStringArray())
|
|
||||||
result := podmanTest.Podman([]string{"events", "--stream=false", "--since", "1h"})
|
|
||||||
result.WaitWithDefaultTimeout()
|
result.WaitWithDefaultTimeout()
|
||||||
Expect(result.ExitCode()).To(BeZero())
|
Expect(result.ExitCode()).To(BeZero())
|
||||||
})
|
})
|
||||||
@ -154,4 +153,40 @@ var _ = Describe("Podman events", func() {
|
|||||||
|
|
||||||
Expect(eventsMap).To(HaveKey("Status"))
|
Expect(eventsMap).To(HaveKey("Status"))
|
||||||
})
|
})
|
||||||
|
|
||||||
|
It("podman events --until future", func() {
|
||||||
|
name1 := stringid.GenerateNonCryptoID()
|
||||||
|
name2 := stringid.GenerateNonCryptoID()
|
||||||
|
name3 := stringid.GenerateNonCryptoID()
|
||||||
|
session := podmanTest.Podman([]string{"create", "--name", name1, ALPINE})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session.ExitCode()).To(Equal(0))
|
||||||
|
|
||||||
|
var wg sync.WaitGroup
|
||||||
|
wg.Add(1)
|
||||||
|
go func() {
|
||||||
|
defer GinkgoRecover()
|
||||||
|
defer wg.Done()
|
||||||
|
|
||||||
|
// wait 2 seconds to be sure events is running
|
||||||
|
time.Sleep(time.Second * 2)
|
||||||
|
session = podmanTest.Podman([]string{"create", "--name", name2, ALPINE})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session.ExitCode()).To(Equal(0))
|
||||||
|
session = podmanTest.Podman([]string{"create", "--name", name3, ALPINE})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session.ExitCode()).To(Equal(0))
|
||||||
|
}()
|
||||||
|
|
||||||
|
// unix timestamp in 10 seconds
|
||||||
|
until := time.Now().Add(time.Second * 10).Unix()
|
||||||
|
result := podmanTest.Podman([]string{"events", "--since", "30s", "--until", fmt.Sprint(until)})
|
||||||
|
result.Wait(11)
|
||||||
|
Expect(result.ExitCode()).To(BeZero())
|
||||||
|
Expect(result.OutputToString()).To(ContainSubstring(name1))
|
||||||
|
Expect(result.OutputToString()).To(ContainSubstring(name2))
|
||||||
|
Expect(result.OutputToString()).To(ContainSubstring(name3))
|
||||||
|
|
||||||
|
wg.Wait()
|
||||||
|
})
|
||||||
})
|
})
|
||||||
|
Reference in New Issue
Block a user