1
- import { type ElectronApplication , type JSHandle } from '@playwright/test' ;
1
+ import type { ElectronApplication , JSHandle , TestInfo } from '@playwright/test' ;
2
2
import electronPath , { type BrowserWindow } from 'electron' ;
3
3
import { _electron as electron } from 'playwright' ;
4
4
5
+ import { createDesktopScreenshot } from '../shared/utils' ;
5
6
import { TestEnvironment } from './testEnvironment' ;
6
7
7
8
// eslint-disable-next-line @typescript-eslint/no-base-to-string
@@ -17,6 +18,16 @@ async function localTestQoL(app: ElectronApplication) {
17
18
window . on ( 'console' , console . log ) ;
18
19
}
19
20
21
+ /** Screen shot entire desktop */
22
+ async function attachScreenshot ( testInfo : TestInfo , name : string ) {
23
+ try {
24
+ const filePath = await createDesktopScreenshot ( name ) ;
25
+ await testInfo . attach ( name , { path : filePath } ) ;
26
+ } catch ( error ) {
27
+ console . error ( error ) ;
28
+ }
29
+ }
30
+
20
31
/**
21
32
* Base class for desktop e2e tests.
22
33
*/
@@ -27,14 +38,17 @@ export class TestApp implements AsyncDisposable {
27
38
/** Remove the install directory when disposed. */
28
39
shouldDisposeTestEnvironment : boolean = false ;
29
40
30
- private constructor ( readonly app : ElectronApplication ) {
41
+ private constructor (
42
+ readonly app : ElectronApplication ,
43
+ readonly testInfo : TestInfo
44
+ ) {
31
45
app . once ( 'close' , ( ) => ( this . #appProcessTerminated = true ) ) ;
32
46
}
33
47
34
48
/** Async static factory */
35
- static async create ( ) {
49
+ static async create ( testInfo : TestInfo ) {
36
50
const app = await TestApp . launchElectron ( ) ;
37
- return new TestApp ( app ) ;
51
+ return new TestApp ( app , testInfo ) ;
38
52
}
39
53
40
54
/** Get the first window that the app opens. Wait if necessary. */
@@ -78,9 +92,15 @@ export class TestApp implements AsyncDisposable {
78
92
const windows = this . app . windows ( ) ;
79
93
if ( windows . length === 0 ) return ;
80
94
81
- const close = this . app . waitForEvent ( 'close' , { timeout : 60 * 1000 } ) ;
82
- await Promise . all ( windows . map ( ( x ) => x . close ( ) ) ) ;
83
- await close ;
95
+ try {
96
+ const close = this . app . waitForEvent ( 'close' , { timeout : 60 * 1000 } ) ;
97
+ await Promise . all ( windows . map ( ( x ) => x . close ( ) ) ) ;
98
+ await close ;
99
+ } catch ( error ) {
100
+ console . error ( 'App failed to close; attaching screenshot to TestInfo' ) ;
101
+ await attachScreenshot ( this . testInfo , 'test-app-close-failure' ) ;
102
+ throw error ;
103
+ }
84
104
}
85
105
86
106
#appProcessTerminated = false ;
0 commit comments