Skip to content

Commit

Permalink
Refactor to work with the filePersister
Browse files Browse the repository at this point in the history
We're refactoring out the existing use of working directly with the os
package to persist screenshots to the local disk from screenshotter.
This change enables to work with the localPersister whereby the
underlying details of the where and how are hidden allowing us to
easily use either the localPersister (current) or the remotePersister
(future).
  • Loading branch information
ankur22 committed Jan 31, 2024
1 parent 31d8e6a commit 0d78912
Show file tree
Hide file tree
Showing 6 changed files with 27 additions and 21 deletions.
12 changes: 8 additions & 4 deletions browser/mapping.go
Original file line number Diff line number Diff line change
Expand Up @@ -279,8 +279,10 @@ func mapElementHandle(vu moduleVU, eh *common.ElementHandle) mapping {
}
return mapFrame(vu, f), nil
},
"press": eh.Press,
"screenshot": eh.Screenshot,
"press": eh.Press,
"screenshot": func(opts goja.Value) goja.ArrayBuffer {
return eh.Screenshot(opts, vu.LocalFilePersister)
},
"scrollIntoViewIfNeeded": eh.ScrollIntoViewIfNeeded,
"selectOption": eh.SelectOption,
"selectText": eh.SelectText,
Expand Down Expand Up @@ -686,8 +688,10 @@ func mapPage(vu moduleVU, p *common.Page) mapping {
r := mapResponse(vu, p.Reload(opts))
return rt.ToValue(r).ToObject(rt)
},
"route": p.Route,
"screenshot": p.Screenshot,
"route": p.Route,
"screenshot": func(opts goja.Value) goja.ArrayBuffer {
return p.Screenshot(opts, vu.LocalFilePersister)
},
"selectOption": p.SelectOption,
"setContent": p.SetContent,
"setDefaultNavigationTimeout": p.SetDefaultNavigationTimeout,
Expand Down
6 changes: 4 additions & 2 deletions common/element_handle.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import (

"github.com/grafana/xk6-browser/common/js"
"github.com/grafana/xk6-browser/k6ext"
"github.com/grafana/xk6-browser/storage"
)

const resultDone = "done"
Expand Down Expand Up @@ -1176,7 +1177,8 @@ func (h *ElementHandle) setChecked(apiCtx context.Context, checked bool, p *Posi
return nil
}

func (h *ElementHandle) Screenshot(opts goja.Value) goja.ArrayBuffer {
// Screenshot will instruct Chrome to save a screenshot of the current element and save it to specified file.
func (h *ElementHandle) Screenshot(opts goja.Value, fp *storage.LocalFilePersister) goja.ArrayBuffer {
spanCtx, span := TraceAPICall(
h.ctx,
h.frame.page.targetID.String(),
Expand All @@ -1191,7 +1193,7 @@ func (h *ElementHandle) Screenshot(opts goja.Value) goja.ArrayBuffer {
}
span.SetAttributes(attribute.String("screenshot.path", parsedOpts.Path))

s := newScreenshotter(spanCtx)
s := newScreenshotter(spanCtx, fp)
buf, err := s.screenshotElement(h, parsedOpts)
if err != nil {
k6ext.Panic(h.ctx, "taking screenshot: %w", err)
Expand Down
5 changes: 3 additions & 2 deletions common/page.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ import (

"github.com/grafana/xk6-browser/k6ext"
"github.com/grafana/xk6-browser/log"
"github.com/grafana/xk6-browser/storage"

k6modules "go.k6.io/k6/js/modules"
)
Expand Down Expand Up @@ -1120,7 +1121,7 @@ func (p *Page) Route(url goja.Value, handler goja.Callable) {
}

// Screenshot will instruct Chrome to save a screenshot of the current page and save it to specified file.
func (p *Page) Screenshot(opts goja.Value) goja.ArrayBuffer {
func (p *Page) Screenshot(opts goja.Value, fp *storage.LocalFilePersister) goja.ArrayBuffer {
spanCtx, span := TraceAPICall(p.ctx, p.targetID.String(), "page.screenshot")
defer span.End()

Expand All @@ -1130,7 +1131,7 @@ func (p *Page) Screenshot(opts goja.Value) goja.ArrayBuffer {
}
span.SetAttributes(attribute.String("screenshot.path", parsedOpts.Path))

s := newScreenshotter(spanCtx)
s := newScreenshotter(spanCtx, fp)
buf, err := s.screenshotPage(p, parsedOpts)
if err != nil {
k6ext.Panic(p.ctx, "capturing screenshot: %w", err)
Expand Down
19 changes: 8 additions & 11 deletions common/screenshotter.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,14 +7,14 @@ import (
"errors"
"fmt"
"math"
"os"
"path/filepath"
"strings"

"github.com/chromedp/cdproto/cdp"
"github.com/chromedp/cdproto/emulation"
cdppage "github.com/chromedp/cdproto/page"
"github.com/dop251/goja"

"github.com/grafana/xk6-browser/storage"
)

// ImageFormat represents an image file format.
Expand Down Expand Up @@ -61,11 +61,12 @@ func (f *ImageFormat) UnmarshalJSON(b []byte) error {
}

type screenshotter struct {
ctx context.Context
ctx context.Context
persister *storage.LocalFilePersister
}

func newScreenshotter(ctx context.Context) *screenshotter {
return &screenshotter{ctx}
func newScreenshotter(ctx context.Context, fp *storage.LocalFilePersister) *screenshotter {
return &screenshotter{ctx, fp}
}

func (s *screenshotter) fullPageSize(p *Page) (*Size, error) {
Expand Down Expand Up @@ -217,12 +218,8 @@ func (s *screenshotter) screenshot(
// Save screenshot capture to file
// TODO: we should not write to disk here but put it on some queue for async disk writes
if path != "" {
dir := filepath.Dir(path)
if err := os.MkdirAll(dir, 0o755); err != nil {
return nil, fmt.Errorf("creating screenshot directory %q: %w", dir, err)
}
if err := os.WriteFile(path, buf, 0o644); err != nil {
return nil, fmt.Errorf("saving screenshot to %q: %w", path, err)
if err := s.persister.Persist(path, bytes.NewBuffer(buf)); err != nil {
return nil, fmt.Errorf("persisting screenshot: %w", err)
}
}

Expand Down
3 changes: 2 additions & 1 deletion tests/element_handle_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import (
"testing"

"github.com/grafana/xk6-browser/common"
"github.com/grafana/xk6-browser/storage"

"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
Expand Down Expand Up @@ -374,7 +375,7 @@ func TestElementHandleScreenshot(t *testing.T) {
elem, err := p.Query("div")
require.NoError(t, err)

buf := elem.Screenshot(nil)
buf := elem.Screenshot(nil, &storage.LocalFilePersister{})

reader := bytes.NewReader(buf.Bytes())
img, err := png.Decode(reader)
Expand Down
3 changes: 2 additions & 1 deletion tests/page_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ import (
"github.com/grafana/xk6-browser/browser"
"github.com/grafana/xk6-browser/common"
"github.com/grafana/xk6-browser/k6ext/k6test"
"github.com/grafana/xk6-browser/storage"
)

type emulateMediaOpts struct {
Expand Down Expand Up @@ -477,7 +478,7 @@ func TestPageScreenshotFullpage(t *testing.T) {
FullPage bool `js:"fullPage"`
}{
FullPage: true,
}))
}), &storage.LocalFilePersister{})

reader := bytes.NewReader(buf.Bytes())
img, err := png.Decode(reader)
Expand Down

0 comments on commit 0d78912

Please sign in to comment.