Skip to content

Commit ae63989

Browse files
committed
Always return result tuples from playwright channel functions
1 parent c4a33fd commit ae63989

File tree

10 files changed

+83
-73
lines changed

10 files changed

+83
-73
lines changed

CHANGELOG.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,11 @@ All notable changes to this project will be documented in this file.
55
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
66
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
77

8+
## tbd
9+
### Changed
10+
- Return result tuples from all playwright channel functions for consistency and to surface errors early.
11+
- Most notably may affect callers of `Frame.evaluate/3`
12+
813
## [0.8.0] 2025-09-17
914
### Removed
1015
- Config option `cli`. Use `assets_dir` instead. Commit [9e95e54]

lib/phoenix_test/playwright.ex

Lines changed: 6 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -230,12 +230,8 @@ defmodule PhoenixTest.Playwright do
230230
231231
defp assert_a11y(conn) do
232232
Frame.evaluate(conn.frame_id, A11yAudit.JS.axe_core())
233-
234-
results =
235-
conn.frame_id
236-
|> Frame.evaluate("axe.run()")
237-
|> A11yAudit.Results.from_json()
238-
233+
{:ok, json} = Frame.evaluate(conn.frame_id, "axe.run()")
234+
results = A11yAudit.Results.from_json(json)
239235
A11yAudit.Assertions.assert_no_violations(results)
240236
241237
conn
@@ -403,7 +399,7 @@ defmodule PhoenixTest.Playwright do
403399
_ -> Application.fetch_env!(:phoenix_test, :base_url) <> path
404400
end
405401

406-
tap(conn, &Frame.goto(&1.frame_id, url))
402+
tap(conn, &({:ok, _} = Frame.goto(&1.frame_id, url)))
407403
end
408404

409405
@doc """
@@ -417,14 +413,14 @@ defmodule PhoenixTest.Playwright do
417413
"""
418414
def add_cookies(conn, cookies) do
419415
cookies = Enum.map(cookies, &CookieArgs.from_cookie/1)
420-
tap(conn, &BrowserContext.add_cookies(&1.context_id, cookies))
416+
tap(conn, &({:ok, _} = BrowserContext.add_cookies(&1.context_id, cookies)))
421417
end
422418

423419
@doc """
424420
Removes all cookies from the context
425421
"""
426422
def clear_cookies(conn, opts \\ []) do
427-
tap(conn, &BrowserContext.clear_cookies(&1.context_id, opts))
423+
tap(conn, &({:ok, _} = BrowserContext.clear_cookies(&1.context_id, opts)))
428424
end
429425

430426
@doc """
@@ -447,7 +443,7 @@ defmodule PhoenixTest.Playwright do
447443
"""
448444
def add_session_cookie(conn, cookie, session_options) do
449445
cookie = CookieArgs.from_session_options(cookie, session_options)
450-
tap(conn, &BrowserContext.add_cookies(&1.context_id, [cookie]))
446+
tap(conn, &({:ok, _} = BrowserContext.add_cookies(&1.context_id, [cookie])))
451447
end
452448

453449
@screenshot_opts_schema [

lib/phoenix_test/playwright/browser.ex

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,9 @@ defmodule PhoenixTest.Playwright.Browser do
1515
"""
1616
def new_context(browser_id, opts \\ []) do
1717
params = Map.new(opts)
18-
resp = post(guid: browser_id, method: :new_context, params: params)
19-
resp.result.context.guid
18+
19+
[guid: browser_id, method: :new_context, params: params]
20+
|> post()
21+
|> PhoenixTest.Playwright.Result.from_response(& &1.result.context.guid)
2022
end
2123
end

lib/phoenix_test/playwright/browser_context.ex

Lines changed: 21 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -10,26 +10,35 @@ defmodule PhoenixTest.Playwright.BrowserContext do
1010

1111
import PhoenixTest.Playwright.Connection, only: [post: 1, initializer: 1]
1212

13+
alias PhoenixTest.Playwright.Result
14+
1315
@doc """
1416
Open a new browser page and return its `guid`.
1517
"""
1618
def new_page(context_id, opts \\ []) do
1719
params = Map.new(opts)
18-
resp = post(guid: context_id, method: :new_page, params: params)
19-
resp.result.page.guid
20+
21+
[guid: context_id, method: :new_page, params: params]
22+
|> post()
23+
|> Result.from_response(& &1.result.page.guid)
2024
end
2125

2226
@doc false
2327
def add_cookies(context_id, cookies) do
24-
post(guid: context_id, method: :add_cookies, params: %{cookies: cookies})
28+
[guid: context_id, method: :add_cookies, params: %{cookies: cookies}]
29+
|> post()
30+
|> Result.from_response(& &1)
2531
end
2632

2733
@doc """
2834
Removes all cookies from the context
2935
"""
3036
def clear_cookies(context_id, opts \\ []) do
3137
opts = Keyword.validate!(opts, ~w(domain name path)a)
32-
post(guid: context_id, method: :clear_cookies, params: Map.new(opts))
38+
39+
[guid: context_id, method: :clear_cookies, params: Map.new(opts)]
40+
|> post()
41+
|> Result.from_response(& &1)
3342
end
3443

3544
@doc """
@@ -39,8 +48,10 @@ defmodule PhoenixTest.Playwright.BrowserContext do
3948
opts = Keyword.validate!(opts, screenshots: true, snapshots: true, sources: true)
4049
tracing_id = initializer(context_id).tracing.guid
4150
post(method: :tracing_start, guid: tracing_id, params: Map.new(opts))
42-
post(method: :tracing_start_chunk, guid: tracing_id)
43-
:ok
51+
52+
[method: :tracing_start_chunk, guid: tracing_id]
53+
|> post()
54+
|> Result.from_response(& &1)
4455
end
4556

4657
@doc """
@@ -56,7 +67,9 @@ defmodule PhoenixTest.Playwright.BrowserContext do
5667
zip_id = resp.result.artifact.guid
5768
zip_path = initializer(zip_id).absolute_path
5869
File.cp!(zip_path, output_path)
59-
post(method: :tracing_stop, guid: tracing_id)
60-
:ok
70+
71+
[method: :tracing_stop, guid: tracing_id]
72+
|> post()
73+
|> Result.from_response(& &1)
6174
end
6275
end

lib/phoenix_test/playwright/case.ex

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -85,11 +85,11 @@ defmodule PhoenixTest.Playwright.Case do
8585
user_agent: checkout_ecto_repos(context.async) || "No user agent"
8686
})
8787

88-
browser_context_id = Playwright.Browser.new_context(context.browser_id, browser_context_opts)
88+
{:ok, browser_context_id} = Playwright.Browser.new_context(context.browser_id, browser_context_opts)
8989

90-
page_id = Playwright.BrowserContext.new_page(browser_context_id, config[:browser_page_opts])
91-
Playwright.Page.update_subscription(page_id, event: :console, enabled: true)
92-
Playwright.Page.update_subscription(page_id, event: :dialog, enabled: true)
90+
{:ok, page_id} = Playwright.BrowserContext.new_page(browser_context_id, config[:browser_page_opts])
91+
{:ok, _} = Playwright.Page.update_subscription(page_id, event: :console, enabled: true)
92+
{:ok, _} = Playwright.Page.update_subscription(page_id, event: :dialog, enabled: true)
9393

9494
frame_id = Connection.initializer(page_id).main_frame.guid
9595
on_exit(fn -> Connection.post(guid: browser_context_id, method: :close) end)
@@ -106,14 +106,14 @@ defmodule PhoenixTest.Playwright.Case do
106106
end
107107

108108
defp trace(browser_context_id, config, context) do
109-
Playwright.BrowserContext.start_tracing(browser_context_id)
109+
{:ok, _} = Playwright.BrowserContext.start_tracing(browser_context_id)
110110

111111
File.mkdir_p!(config[:trace_dir])
112112
file = file_name("_#{System.unique_integer([:positive, :monotonic])}.zip", context)
113113
path = Path.join(config[:trace_dir], file)
114114

115115
on_exit(fn ->
116-
Playwright.BrowserContext.stop_tracing(browser_context_id, path)
116+
_ignore_error = Playwright.BrowserContext.stop_tracing(browser_context_id, path)
117117

118118
if config[:trace] == :open do
119119
System.cmd(

lib/phoenix_test/playwright/dialog.ex

Lines changed: 4 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -10,22 +10,17 @@ defmodule PhoenixTest.Playwright.Dialog do
1010

1111
import PhoenixTest.Playwright.Connection, only: [post: 1]
1212

13+
alias PhoenixTest.Playwright.Result
14+
1315
def accept(dialog_id, opts \\ []) do
1416
[guid: dialog_id, method: :accept, params: Map.new(opts)]
1517
|> post()
16-
|> unwrap_response(& &1)
18+
|> Result.from_response(& &1)
1719
end
1820

1921
def dismiss(dialog_id, opts \\ []) do
2022
[guid: dialog_id, method: :dismiss, params: Map.new(opts)]
2123
|> post()
22-
|> unwrap_response(& &1)
23-
end
24-
25-
defp unwrap_response(response, fun) do
26-
case response do
27-
%{error: _} = error -> {:error, error}
28-
_ -> {:ok, fun.(response)}
29-
end
24+
|> Result.from_response(& &1)
3025
end
3126
end

lib/phoenix_test/playwright/frame.ex

Lines changed: 22 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -11,18 +11,21 @@ defmodule PhoenixTest.Playwright.Frame do
1111
import PhoenixTest.Playwright.Connection, only: [post: 1, post: 2]
1212

1313
alias PhoenixTest.Playwright.Config
14+
alias PhoenixTest.Playwright.Result
1415
alias PhoenixTest.Playwright.Serialization
1516

1617
def goto(frame_id, url) do
1718
params = %{url: url}
18-
post(guid: frame_id, method: :goto, params: params)
19-
:ok
19+
20+
[guid: frame_id, method: :goto, params: params]
21+
|> post()
22+
|> Result.from_response(& &1)
2023
end
2124

2225
def url(frame_id) do
2326
[guid: frame_id, method: :url, params: %{}]
2427
|> post()
25-
|> unwrap_response(& &1.result.value)
28+
|> Result.from_response(& &1.result.value)
2629
end
2730

2831
def evaluate(frame_id, js, opts \\ []) do
@@ -33,8 +36,8 @@ defmodule PhoenixTest.Playwright.Frame do
3336

3437
[guid: frame_id, method: :evaluate_expression, params: params]
3538
|> post()
36-
|> unwrap_response(& &1.result.value)
37-
|> Serialization.deserialize_arg()
39+
|> Result.from_response(& &1.result.value)
40+
|> Result.map(&Serialization.deserialize_arg/1)
3841
end
3942

4043
def press(frame_id, selector, key, opts \\ []) do
@@ -45,7 +48,7 @@ defmodule PhoenixTest.Playwright.Frame do
4548

4649
[guid: frame_id, method: :press, params: params]
4750
|> post(timeout)
48-
|> unwrap_response(& &1)
51+
|> Result.from_response(& &1)
4952
end
5053

5154
def type(frame_id, selector, text, opts \\ []) do
@@ -56,41 +59,41 @@ defmodule PhoenixTest.Playwright.Frame do
5659

5760
[guid: frame_id, method: :type, params: params]
5861
|> post(timeout)
59-
|> unwrap_response(& &1)
62+
|> Result.from_response(& &1)
6063
end
6164

6265
def title(frame_id) do
6366
[guid: frame_id, method: :title]
6467
|> post()
65-
|> unwrap_response(& &1.result.value)
68+
|> Result.from_response(& &1.result.value)
6669
end
6770

6871
def expect(frame_id, params) do
6972
params = Enum.into(params, %{is_not: false})
7073

7174
[guid: frame_id, method: :expect, params: params]
7275
|> post()
73-
|> unwrap_response(& &1.result.matches)
76+
|> Result.from_response(& &1.result.matches)
7477
end
7578

7679
def wait_for_selector(frame_id, params) do
7780
[guid: frame_id, method: :wait_for_selector, params: params]
7881
|> post()
79-
|> unwrap_response(& &1.result.element)
82+
|> Result.from_response(& &1.result.element)
8083
end
8184

8285
def inner_html(frame_id, selector) do
8386
params = %{selector: selector}
8487

8588
[guid: frame_id, method: "innerHTML", params: params]
8689
|> post()
87-
|> unwrap_response(& &1.result.value)
90+
|> Result.from_response(& &1.result.value)
8891
end
8992

9093
def content(frame_id) do
9194
[guid: frame_id, method: :content]
9295
|> post()
93-
|> unwrap_response(& &1.result.value)
96+
|> Result.from_response(& &1.result.value)
9497
end
9598

9699
def fill(frame_id, selector, value, opts \\ []) do
@@ -99,7 +102,7 @@ defmodule PhoenixTest.Playwright.Frame do
99102

100103
[guid: frame_id, method: :fill, params: params]
101104
|> post()
102-
|> unwrap_response(& &1)
105+
|> Result.from_response(& &1)
103106
end
104107

105108
def select_option(frame_id, selector, options, opts \\ []) do
@@ -108,7 +111,7 @@ defmodule PhoenixTest.Playwright.Frame do
108111

109112
[guid: frame_id, method: :select_option, params: params]
110113
|> post()
111-
|> unwrap_response(& &1)
114+
|> Result.from_response(& &1)
112115
end
113116

114117
def check(frame_id, selector, opts \\ []) do
@@ -117,7 +120,7 @@ defmodule PhoenixTest.Playwright.Frame do
117120

118121
[guid: frame_id, method: :check, params: params]
119122
|> post()
120-
|> unwrap_response(& &1)
123+
|> Result.from_response(& &1)
121124
end
122125

123126
def uncheck(frame_id, selector, opts \\ []) do
@@ -126,7 +129,7 @@ defmodule PhoenixTest.Playwright.Frame do
126129

127130
[guid: frame_id, method: :uncheck, params: params]
128131
|> post()
129-
|> unwrap_response(& &1)
132+
|> Result.from_response(& &1)
130133
end
131134

132135
def set_input_files(frame_id, selector, paths, opts \\ []) do
@@ -135,7 +138,7 @@ defmodule PhoenixTest.Playwright.Frame do
135138

136139
[guid: frame_id, method: :set_input_files, params: params]
137140
|> post()
138-
|> unwrap_response(& &1)
141+
|> Result.from_response(& &1)
139142
end
140143

141144
def click(frame_id, selector, opts \\ []) do
@@ -144,7 +147,7 @@ defmodule PhoenixTest.Playwright.Frame do
144147

145148
[guid: frame_id, method: :click, params: params]
146149
|> post()
147-
|> unwrap_response(& &1)
150+
|> Result.from_response(& &1)
148151
end
149152

150153
def blur(frame_id, selector, opts \\ []) do
@@ -153,13 +156,6 @@ defmodule PhoenixTest.Playwright.Frame do
153156

154157
[guid: frame_id, method: :blur, params: params]
155158
|> post()
156-
|> unwrap_response(& &1)
157-
end
158-
159-
defp unwrap_response(response, fun) do
160-
case response do
161-
%{error: _} = error -> {:error, error}
162-
_ -> {:ok, fun.(response)}
163-
end
159+
|> Result.from_response(& &1)
164160
end
165161
end

lib/phoenix_test/playwright/page.ex

Lines changed: 6 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,12 @@ defmodule PhoenixTest.Playwright.Page do
1010

1111
import PhoenixTest.Playwright.Connection, only: [post: 1]
1212

13+
alias PhoenixTest.Playwright.Result
14+
1315
def update_subscription(page_id, opts \\ []) do
14-
post(guid: page_id, method: :update_subscription, params: Map.new(opts))
16+
[guid: page_id, method: :update_subscription, params: Map.new(opts)]
17+
|> post()
18+
|> Result.from_response(& &1)
1519
end
1620

1721
def screenshot(page_id, opts \\ []) do
@@ -23,13 +27,6 @@ defmodule PhoenixTest.Playwright.Page do
2327

2428
[guid: page_id, method: :screenshot, params: params]
2529
|> post()
26-
|> unwrap_response(& &1.result.binary)
27-
end
28-
29-
defp unwrap_response(response, fun) do
30-
case response do
31-
%{error: _} = error -> {:error, error}
32-
_ -> {:ok, fun.(response)}
33-
end
30+
|> Result.from_response(& &1.result.binary)
3431
end
3532
end
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
defmodule PhoenixTest.Playwright.Result do
2+
@moduledoc false
3+
4+
def from_response(%{error: _} = error, _), do: {:error, error}
5+
def from_response(value, fun) when is_function(fun, 1), do: {:ok, fun.(value)}
6+
7+
def map({:error, error}, _), do: {:error, error}
8+
def map({:ok, value}, fun) when is_function(fun, 1), do: {:ok, fun.(value)}
9+
end

0 commit comments

Comments
 (0)