我有这个FileReader,可以用来阅读文件夹:
private fileCache: any[];
private folderReader$: Subject<any[]> = new Subject();
public readFolder(files: any[]) {
this.fileCache = [];
this.readFile(0, files);
return this.folderReader$.asObservable();
}
private readFile(index, files) {
const reader = new FileReader();
if (index >= files.length) {
this.folderReader$.next(this.fileCache);
return;
}
const file = files[index];
const filename = file.name;
reader.onload = (e: any) => {
this.fileCache.push({
name: filename,
content: e.target.result});
this.readFile(index+ 1, files);
};
reader.readAsText(file);
}
}
现在奇怪的是,每当我选择第二个输入时,它都会运行多次。如果我只选择一个输入,一切都很好...
例如,当使用此命令时:
this.folderReader.readFolder(data.target.files).subscribe(files => {
console.log(test);
}
仅输入两次后,控制台将显示三次测试:
test
test
test
就像我在这里看到的那样:File reader execute multiple times in javascript可能与onload运行多次有关,所以我尝试删除此行:
this.readFile(index+ 1, files);
这样整个功能就不会重新开始...
但是,在那之后,它根本不起作用,因为它可能需要index+1
,因此它可以处理我认为的所有文件。
我在这里做错了什么?为什么FileReader会多次执行自身而不是每次输入仅执行一次?
答案 0 :(得分:2)
这是您处理主题的方式。
一种解决方法是在readFolder调用中重新初始化您的Subject,例如:
public readFolder(files: any[]) {
this.folderReader$ = new Subject();
this.fileCache = [];
this.readFile(0, files);
return this.folderReader$.asObservable();
}
但是更好的方法是使用另一个主题,例如rxjs中的BehaviorSubject。
看看Understanding rxjs BehaviorSubject, ReplaySubject and AsyncSubject