@@ -78,6 +78,7 @@ defmodule Sentry.Test do
7878
7979 @ server __MODULE__ . OwnershipServer
8080 @ key :events
81+ @ transaction_key :transactions
8182
8283 # Used internally when reporting an event, *before* reporting the actual event.
8384 @ doc false
@@ -115,6 +116,48 @@ defmodule Sentry.Test do
115116 end
116117 end
117118
119+ # Used internally when reporting a transaction, *before* reporting the actual transaction.
120+ @ doc false
121+ @ spec maybe_collect ( Sentry.Transaction . t ( ) ) :: :collected | :not_collecting
122+ def maybe_collect ( % Sentry.Transaction { } = transaction ) do
123+ if Sentry.Config . test_mode? ( ) do
124+ dsn_set? = not is_nil ( Sentry.Config . dsn ( ) )
125+ ensure_ownership_server_started ( )
126+
127+ case NimbleOwnership . fetch_owner ( @ server , callers ( ) , @ transaction_key ) do
128+ { :ok , owner_pid } ->
129+ result =
130+ NimbleOwnership . get_and_update (
131+ @ server ,
132+ owner_pid ,
133+ @ transaction_key ,
134+ fn transactions ->
135+ { :collected , ( transactions || [ ] ) ++ [ transaction ] }
136+ end
137+ )
138+
139+ case result do
140+ { :ok , :collected } ->
141+ :collected
142+
143+ { :error , error } ->
144+ raise ArgumentError ,
145+ "cannot collect Sentry transactions: #{ Exception . message ( error ) } "
146+ end
147+
148+ :error when dsn_set? ->
149+ :not_collecting
150+
151+ # If the :dsn option is not set and we didn't capture the transaction, it's alright,
152+ # we can just swallow it.
153+ :error ->
154+ :collected
155+ end
156+ else
157+ :not_collecting
158+ end
159+ end
160+
118161 @ doc """
119162 Starts collecting events from the current process.
120163
@@ -135,7 +178,8 @@ defmodule Sentry.Test do
135178 @ doc since: "10.2.0"
136179 @ spec start_collecting_sentry_reports ( map ( ) ) :: :ok
137180 def start_collecting_sentry_reports ( _context \\ % { } ) do
138- start_collecting ( )
181+ start_collecting ( key: @ key )
182+ start_collecting ( key: @ transaction_key )
139183 end
140184
141185 @ doc """
@@ -177,6 +221,7 @@ defmodule Sentry.Test do
177221 @ doc since: "10.2.0"
178222 @ spec start_collecting ( keyword ( ) ) :: :ok
179223 def start_collecting ( options \\ [ ] ) when is_list ( options ) do
224+ key = Keyword . get ( options , :key , @ key )
180225 owner_pid = Keyword . get ( options , :owner , self ( ) )
181226 cleanup? = Keyword . get ( options , :cleanup , true )
182227
@@ -190,7 +235,7 @@ defmodule Sentry.Test do
190235 # Make sure the ownership server is started (this is idempotent).
191236 ensure_ownership_server_started ( )
192237
193- case NimbleOwnership . fetch_owner ( @ server , callers , @ key ) do
238+ case NimbleOwnership . fetch_owner ( @ server , callers , key ) do
194239 # No-op
195240 { tag , ^ owner_pid } when tag in [ :ok , :shared_owner ] ->
196241 :ok
@@ -207,7 +252,7 @@ defmodule Sentry.Test do
207252 end
208253
209254 { :ok , _ } =
210- NimbleOwnership . get_and_update ( @ server , self ( ) , @ key , fn events ->
255+ NimbleOwnership . get_and_update ( @ server , self ( ) , key , fn events ->
211256 { :ignored , events || [ ] }
212257 end )
213258
@@ -302,6 +347,51 @@ defmodule Sentry.Test do
302347 end
303348 end
304349
350+ @ doc """
351+ Pops all the collected transactions from the current process.
352+
353+ This function returns a list of all the transactions that have been collected from the current
354+ process and all the processes that were allowed through it. If the current process
355+ is not collecting transactions, this function raises an error.
356+
357+ After this function returns, the current process will still be collecting transactions, but
358+ the collected transactions will be reset to `[]`.
359+
360+ ## Examples
361+
362+ iex> Sentry.Test.start_collecting_sentry_reports()
363+ :ok
364+ iex> Sentry.send_transaction(Sentry.Transaction.new(%{span_id: "123", spans: []}))
365+ {:ok, ""}
366+ iex> [%Sentry.Transaction{}] = Sentry.Test.pop_sentry_transactions()
367+
368+ """
369+ @ doc since: "10.2.0"
370+ @ spec pop_sentry_transactions ( pid ( ) ) :: [ Sentry.Transaction . t ( ) ]
371+ def pop_sentry_transactions ( owner_pid \\ self ( ) ) when is_pid ( owner_pid ) do
372+ result =
373+ try do
374+ NimbleOwnership . get_and_update ( @ server , owner_pid , @ transaction_key , fn
375+ nil -> { :not_collecting , [ ] }
376+ transactions when is_list ( transactions ) -> { transactions , [ ] }
377+ end )
378+ catch
379+ :exit , { :noproc , _ } ->
380+ raise ArgumentError , "not collecting reported transactions from #{ inspect ( owner_pid ) } "
381+ end
382+
383+ case result do
384+ { :ok , :not_collecting } ->
385+ raise ArgumentError , "not collecting reported transactions from #{ inspect ( owner_pid ) } "
386+
387+ { :ok , transactions } ->
388+ transactions
389+
390+ { :error , error } when is_exception ( error ) ->
391+ raise ArgumentError , "cannot pop Sentry transactions: #{ Exception . message ( error ) } "
392+ end
393+ end
394+
305395 ## Helpers
306396
307397 defp ensure_ownership_server_started do
0 commit comments