@@ -19,6 +19,8 @@ import (
19
19
"github.com/go-task/task/v3/internal/fingerprint"
20
20
"github.com/go-task/task/v3/internal/fsnotifyext"
21
21
"github.com/go-task/task/v3/internal/logger"
22
+ "github.com/go-task/task/v3/internal/slicesext"
23
+ "github.com/go-task/task/v3/taskfile/ast"
22
24
)
23
25
24
26
const defaultWaitTime = 100 * time .Millisecond
@@ -85,17 +87,22 @@ func (e *Executor) watchTasks(calls ...*Call) error {
85
87
for _ , c := range calls {
86
88
c := c
87
89
go func () {
90
+ if ShouldIgnore (event .Name ) {
91
+ e .Logger .VerboseErrf (logger .Magenta , "task: event skipped for being an ignored dir: %s\n " , event .Name )
92
+ return
93
+ }
88
94
t , err := e .GetTask (c )
89
95
if err != nil {
90
96
e .Logger .Errf (logger .Red , "%v\n " , err )
91
97
return
92
98
}
93
99
baseDir := filepathext .SmartJoin (e .Dir , t .Dir )
94
- files , err := fingerprint . Globs ( baseDir , t . Sources )
100
+ files , err := e . collectSources ( calls )
95
101
if err != nil {
96
102
e .Logger .Errf (logger .Red , "%v\n " , err )
97
103
return
98
104
}
105
+
99
106
if ! event .Has (fsnotify .Remove ) && ! slices .Contains (files , event .Name ) {
100
107
relPath , _ := filepath .Rel (baseDir , event .Name )
101
108
e .Logger .VerboseErrf (logger .Magenta , "task: skipped for file not in sources: %s\n " , relPath )
@@ -158,69 +165,86 @@ func closeOnInterrupt(w *fsnotify.Watcher) {
158
165
}
159
166
160
167
func (e * Executor ) registerWatchedDirs (w * fsnotify.Watcher , calls ... * Call ) error {
161
- var registerTaskDirs func (* Call ) error
162
- registerTaskDirs = func (c * Call ) error {
163
- task , err := e .CompiledTask (c )
164
- if err != nil {
168
+ files , err := e .collectSources (calls )
169
+ if err != nil {
170
+ return err
171
+ }
172
+ for _ , f := range files {
173
+ d := filepath .Dir (f )
174
+ if isSet , ok := e .watchedDirs .Load (d ); ok && isSet {
175
+ continue
176
+ }
177
+ if ShouldIgnore (d ) {
178
+ continue
179
+ }
180
+ if err := w .Add (d ); err != nil {
165
181
return err
166
182
}
183
+ e .watchedDirs .Store (d , true )
184
+ relPath , _ := filepath .Rel (e .Dir , d )
185
+ e .Logger .VerboseOutf (logger .Green , "task: watching new dir: %v\n " , relPath )
186
+ }
187
+ return nil
188
+ }
167
189
168
- for _ , d := range task .Deps {
169
- if err := registerTaskDirs (& Call {Task : d .Task , Vars : d .Vars }); err != nil {
170
- return err
171
- }
172
- }
173
- for _ , c := range task .Cmds {
174
- if c .Task != "" {
175
- if err := registerTaskDirs (& Call {Task : c .Task , Vars : c .Vars }); err != nil {
176
- return err
177
- }
178
- }
190
+ var ignorePaths = []string {
191
+ "/.task" ,
192
+ "/.git" ,
193
+ "/.hg" ,
194
+ "/node_modules" ,
195
+ }
196
+
197
+ func ShouldIgnore (path string ) bool {
198
+ println ("path" , path )
199
+
200
+ for _ , p := range ignorePaths {
201
+ if strings .Contains (path , fmt .Sprintf ("%s/" , p )) || strings .HasSuffix (path , p ) {
202
+ return true
179
203
}
204
+ }
205
+ return false
206
+ }
207
+
208
+ func (e * Executor ) collectSources (calls []* Call ) ([]string , error ) {
209
+ var sources []string
180
210
211
+ err := e .traverse (calls , func (task * ast.Task ) error {
181
212
files , err := fingerprint .Globs (task .Dir , task .Sources )
182
213
if err != nil {
183
214
return err
184
215
}
216
+ sources = append (sources , files ... )
217
+ return nil
218
+ })
185
219
186
- for _ , f := range files {
187
- d := filepath .Dir (f )
188
- if isSet , ok := e .watchedDirs .Load (d ); ok && isSet {
189
- continue
190
- }
191
- if ShouldIgnoreFile (d ) {
192
- continue
220
+ return slicesext .UniqueJoin (sources ), err
221
+ }
222
+
223
+ type traverseFunc func (* ast.Task ) error
224
+
225
+ func (e * Executor ) traverse (calls []* Call , yield traverseFunc ) error {
226
+ for _ , c := range calls {
227
+ task , err := e .CompiledTask (c )
228
+ if err != nil {
229
+ return err
230
+ }
231
+ for _ , dep := range task .Deps {
232
+ if dep .Task != "" {
233
+ if err := e .traverse ([]* Call {{Task : dep .Task , Vars : dep .Vars }}, yield ); err != nil {
234
+ return err
235
+ }
193
236
}
194
- if err := w .Add (d ); err != nil {
195
- return err
237
+ }
238
+ for _ , cmd := range task .Cmds {
239
+ if cmd .Task != "" {
240
+ if err := e .traverse ([]* Call {{Task : cmd .Task , Vars : cmd .Vars }}, yield ); err != nil {
241
+ return err
242
+ }
196
243
}
197
- e .watchedDirs .Store (d , true )
198
- relPath , _ := filepath .Rel (e .Dir , d )
199
- w .Events <- fsnotify.Event {Name : f , Op : fsnotify .Create }
200
- e .Logger .VerboseOutf (logger .Green , "task: watching new dir: %v\n " , relPath )
201
244
}
202
- return nil
203
- }
204
-
205
- for _ , c := range calls {
206
- if err := registerTaskDirs (c ); err != nil {
245
+ if err := yield (task ); err != nil {
207
246
return err
208
247
}
209
248
}
210
249
return nil
211
250
}
212
-
213
- func ShouldIgnoreFile (path string ) bool {
214
- ignorePaths := []string {
215
- "/.task" ,
216
- "/.git" ,
217
- "/.hg" ,
218
- "/node_modules" ,
219
- }
220
- for _ , p := range ignorePaths {
221
- if strings .Contains (path , fmt .Sprintf ("%s/" , p )) || strings .HasSuffix (path , p ) {
222
- return true
223
- }
224
- }
225
- return false
226
- }
0 commit comments