@@ -2,6 +2,7 @@ import * as path from "path";
2
2
import { FilePayload , Device , FilesPayload } from "nativescript-preview-sdk" ;
3
3
import { PreviewSdkEventNames } from "./preview-app-constants" ;
4
4
import { APP_FOLDER_NAME , APP_RESOURCES_FOLDER_NAME , TNS_MODULES_FOLDER_NAME } from "../../../constants" ;
5
+ import { HmrConstants } from "../../../common/constants" ;
5
6
const isTextOrBinary = require ( 'istextorbinary' ) ;
6
7
7
8
export class PreviewAppLiveSyncService implements IPreviewAppLiveSyncService {
@@ -19,6 +20,7 @@ export class PreviewAppLiveSyncService implements IPreviewAppLiveSyncService {
19
20
private $previewSdkService : IPreviewSdkService ,
20
21
private $previewAppPluginsService : IPreviewAppPluginsService ,
21
22
private $projectFilesManager : IProjectFilesManager ,
23
+ private $hmrStatusService : IHmrStatusService ,
22
24
private $projectFilesProvider : IProjectFilesProvider ) { }
23
25
24
26
public async initialize ( data : IPreviewAppLiveSyncData ) : Promise < void > {
@@ -43,19 +45,37 @@ export class PreviewAppLiveSyncService implements IPreviewAppLiveSyncService {
43
45
44
46
private async initializePreviewForDevice ( data : IPreviewAppLiveSyncData , device : Device ) : Promise < FilesPayload > {
45
47
const filesToSyncMap : IDictionary < string [ ] > = { } ;
48
+ const hmrData : { hash : string ; fallbackFiles : IDictionary < string [ ] > } = {
49
+ hash : "" ,
50
+ fallbackFiles : { }
51
+ } ;
46
52
let promise = Promise . resolve < FilesPayload > ( null ) ;
47
53
const startSyncFilesTimeout = async ( platform : string ) => {
48
54
await promise
49
55
. then ( async ( ) => {
50
56
const projectData = this . $projectDataService . getProjectData ( data . projectDir ) ;
51
- promise = this . applyChanges ( this . $platformsData . getPlatformData ( platform , projectData ) , projectData , filesToSyncMap [ platform ] ) ;
57
+ const platformData = this . $platformsData . getPlatformData ( platform , projectData ) ;
58
+ const currentHmrData = _ . cloneDeep ( hmrData ) ;
59
+ const filesToSync = _ . cloneDeep ( filesToSyncMap [ platform ] ) ;
60
+ promise = this . applyChanges ( platformData , projectData , filesToSync , data . appFilesUpdaterOptions . useHotModuleReload ) ;
52
61
await promise ;
62
+
63
+ if ( data . appFilesUpdaterOptions . useHotModuleReload && currentHmrData . hash ) {
64
+ const devices = _ . filter ( this . $previewSdkService . connectedDevices , { platform : platform . toLowerCase ( ) } ) ;
65
+ _ . forEach ( devices , async ( previewDevice : Device ) => {
66
+ const status = await this . $hmrStatusService . awaitHmrStatus ( previewDevice . id , currentHmrData . hash ) ;
67
+ if ( status === HmrConstants . HMR_ERROR_STATUS ) {
68
+ await this . applyChanges ( platformData , projectData , currentHmrData . fallbackFiles [ platform ] , false ) ;
69
+ }
70
+ } ) ;
71
+ }
53
72
} ) ;
54
73
filesToSyncMap [ platform ] = [ ] ;
55
74
} ;
56
75
await this . $hooksService . executeBeforeHooks ( "preview-sync" , {
57
76
hookArgs : {
58
77
projectData : this . $projectDataService . getProjectData ( data . projectDir ) ,
78
+ hmrData,
59
79
config : {
60
80
env : data . env ,
61
81
platform : device . platform ,
@@ -104,10 +124,11 @@ export class PreviewAppLiveSyncService implements IPreviewAppLiveSyncService {
104
124
105
125
let result : FilesPayload = null ;
106
126
if ( files && files . length ) {
107
- result = await this . applyChanges ( platformData , projectData , files ) ;
127
+ result = await this . applyChanges ( platformData , projectData , files , data . appFilesUpdaterOptions . useHotModuleReload ) ;
108
128
this . $logger . info ( `Successfully synced ${ result . files . map ( filePayload => filePayload . file . yellow ) } for platform ${ platform } .` ) ;
109
129
} else {
110
- result = await this . getFilesPayload ( platformData , projectData ) ;
130
+ const hmrMode = data . appFilesUpdaterOptions . useHotModuleReload ? 1 : 0 ;
131
+ result = await this . getFilesPayload ( platformData , projectData , hmrMode ) ;
111
132
this . $logger . info ( `Successfully synced changes for platform ${ platform } .` ) ;
112
133
}
113
134
@@ -117,14 +138,15 @@ export class PreviewAppLiveSyncService implements IPreviewAppLiveSyncService {
117
138
}
118
139
}
119
140
120
- private async applyChanges ( platformData : IPlatformData , projectData : IProjectData , files : string [ ] ) : Promise < FilesPayload > {
121
- const payloads = this . getFilesPayload ( platformData , projectData , _ ( files ) . uniq ( ) . value ( ) ) ;
141
+ private async applyChanges ( platformData : IPlatformData , projectData : IProjectData , files : string [ ] , useHotModuleReload : Boolean , deviceId ?: string ) : Promise < FilesPayload > {
142
+ const hmrMode = useHotModuleReload ? 1 : 0 ;
143
+ const payloads = this . getFilesPayload ( platformData , projectData , hmrMode , _ ( files ) . uniq ( ) . value ( ) , deviceId ) ;
122
144
await this . $previewSdkService . applyChanges ( payloads ) ;
123
145
124
146
return payloads ;
125
147
}
126
148
127
- private getFilesPayload ( platformData : IPlatformData , projectData : IProjectData , files ?: string [ ] ) : FilesPayload {
149
+ private getFilesPayload ( platformData : IPlatformData , projectData : IProjectData , hmrMode : number , files ?: string [ ] , deviceId ?: string ) : FilesPayload {
128
150
const platformsAppFolderPath = path . join ( platformData . appDestinationDirectoryPath , APP_FOLDER_NAME ) ;
129
151
130
152
if ( files && files . length ) {
@@ -163,7 +185,7 @@ export class PreviewAppLiveSyncService implements IPreviewAppLiveSyncService {
163
185
return filePayload ;
164
186
} ) ;
165
187
166
- return { files : payloads , platform : platformData . normalizedPlatformName . toLowerCase ( ) } ;
188
+ return { files : payloads , platform : platformData . normalizedPlatformName . toLowerCase ( ) , hmrMode , deviceId } ;
167
189
}
168
190
169
191
private async preparePlatform ( platform : string , appFilesUpdaterOptions : IAppFilesUpdaterOptions , env : Object , projectData : IProjectData ) : Promise < void > {
0 commit comments