Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
掘金者说
vscode
提交
9f6518c5
V
vscode
项目概览
掘金者说
/
vscode
与 Fork 源项目一致
从无法访问的项目Fork
通知
1
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
DevOps
流水线
流水线任务
计划
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
V
vscode
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
DevOps
DevOps
流水线
流水线任务
计划
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
流水线任务
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
9f6518c5
编写于
11月 01, 2019
作者:
J
Johannes Rieken
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
move events back to textfile service
上级
7af36eb6
变更
7
隐藏空白更改
内联
并排
Showing
7 changed file
with
84 addition
and
98 deletion
+84
-98
src/vs/platform/files/common/fileService.ts
src/vs/platform/files/common/fileService.ts
+2
-20
src/vs/platform/files/common/files.ts
src/vs/platform/files/common/files.ts
+1
-23
src/vs/platform/files/test/node/diskFileService.test.ts
src/vs/platform/files/test/node/diskFileService.test.ts
+1
-38
src/vs/workbench/api/browser/mainThreadFileSystemEventService.ts
...workbench/api/browser/mainThreadFileSystemEventService.ts
+10
-8
src/vs/workbench/services/textfile/browser/textFileService.ts
...vs/workbench/services/textfile/browser/textFileService.ts
+29
-5
src/vs/workbench/services/textfile/common/textfiles.ts
src/vs/workbench/services/textfile/common/textfiles.ts
+41
-2
src/vs/workbench/test/workbenchTestServices.ts
src/vs/workbench/test/workbenchTestServices.ts
+0
-2
未找到文件。
src/vs/platform/files/common/fileService.ts
浏览文件 @
9f6518c5
...
...
@@ -4,9 +4,9 @@
*--------------------------------------------------------------------------------------------*/
import
{
Disposable
,
IDisposable
,
toDisposable
,
dispose
,
DisposableStore
}
from
'
vs/base/common/lifecycle
'
;
import
{
IFileService
,
IResolveFileOptions
,
FileChangesEvent
,
FileOperationEvent
,
IFileSystemProviderRegistrationEvent
,
IFileSystemProvider
,
IFileStat
,
IResolveFileResult
,
ICreateFileOptions
,
IFileSystemProviderActivationEvent
,
FileOperationError
,
FileOperationResult
,
FileOperation
,
FileSystemProviderCapabilities
,
FileType
,
toFileSystemProviderErrorCode
,
FileSystemProviderErrorCode
,
IStat
,
IFileStatWithMetadata
,
IResolveMetadataFileOptions
,
etag
,
hasReadWriteCapability
,
hasFileFolderCopyCapability
,
hasOpenReadWriteCloseCapability
,
toFileOperationResult
,
IFileSystemProviderWithOpenReadWriteCloseCapability
,
IFileSystemProviderWithFileReadWriteCapability
,
IResolveFileResultWithMetadata
,
IWatchOptions
,
IWriteFileOptions
,
IReadFileOptions
,
IFileStreamContent
,
IFileContent
,
ETAG_DISABLED
,
FileOperationWillRunEvent
}
from
'
vs/platform/files/common/files
'
;
import
{
IFileService
,
IResolveFileOptions
,
FileChangesEvent
,
FileOperationEvent
,
IFileSystemProviderRegistrationEvent
,
IFileSystemProvider
,
IFileStat
,
IResolveFileResult
,
ICreateFileOptions
,
IFileSystemProviderActivationEvent
,
FileOperationError
,
FileOperationResult
,
FileOperation
,
FileSystemProviderCapabilities
,
FileType
,
toFileSystemProviderErrorCode
,
FileSystemProviderErrorCode
,
IStat
,
IFileStatWithMetadata
,
IResolveMetadataFileOptions
,
etag
,
hasReadWriteCapability
,
hasFileFolderCopyCapability
,
hasOpenReadWriteCloseCapability
,
toFileOperationResult
,
IFileSystemProviderWithOpenReadWriteCloseCapability
,
IFileSystemProviderWithFileReadWriteCapability
,
IResolveFileResultWithMetadata
,
IWatchOptions
,
IWriteFileOptions
,
IReadFileOptions
,
IFileStreamContent
,
IFileContent
,
ETAG_DISABLED
}
from
'
vs/platform/files/common/files
'
;
import
{
URI
}
from
'
vs/base/common/uri
'
;
import
{
Event
,
Emitter
,
AsyncEmitter
}
from
'
vs/base/common/event
'
;
import
{
Event
,
Emitter
}
from
'
vs/base/common/event
'
;
import
{
isAbsolutePath
,
dirname
,
basename
,
joinPath
,
isEqual
,
isEqualOrParent
}
from
'
vs/base/common/resources
'
;
import
{
localize
}
from
'
vs/nls
'
;
import
{
TernarySearchTree
}
from
'
vs/base/common/map
'
;
...
...
@@ -131,9 +131,6 @@ export class FileService extends Disposable implements IFileService {
//#endregion
private
_onWillRunOperation
=
this
.
_register
(
new
AsyncEmitter
<
FileOperationWillRunEvent
>
());
readonly
onWillRunOperation
=
this
.
_onWillRunOperation
.
event
;
private
_onAfterOperation
:
Emitter
<
FileOperationEvent
>
=
this
.
_register
(
new
Emitter
<
FileOperationEvent
>
());
readonly
onAfterOperation
:
Event
<
FileOperationEvent
>
=
this
.
_onAfterOperation
.
event
;
...
...
@@ -282,9 +279,6 @@ export class FileService extends Disposable implements IFileService {
throw
new
FileOperationError
(
localize
(
'
fileExists
'
,
"
File to create already exists ({0})
"
,
this
.
resourceForError
(
resource
)),
FileOperationResult
.
FILE_MODIFIED_SINCE
,
options
);
}
// before events
await
this
.
_onWillRunOperation
.
fireAsync
(
promises
=>
new
FileOperationWillRunEvent
(
promises
,
FileOperation
.
CREATE
,
resource
));
// do write into file (this will create it too)
const
fileStat
=
await
this
.
writeFile
(
resource
,
bufferOrReadableOrStream
);
...
...
@@ -548,9 +542,6 @@ export class FileService extends Disposable implements IFileService {
const
sourceProvider
=
this
.
throwIfFileSystemIsReadonly
(
await
this
.
withReadWriteProvider
(
source
));
const
targetProvider
=
this
.
throwIfFileSystemIsReadonly
(
await
this
.
withReadWriteProvider
(
target
));
// before events
await
this
.
_onWillRunOperation
.
fireAsync
(
promises
=>
new
FileOperationWillRunEvent
(
promises
,
FileOperation
.
MOVE
,
target
,
source
));
// move
const
mode
=
await
this
.
doMoveCopy
(
sourceProvider
,
source
,
targetProvider
,
target
,
'
move
'
,
!!
overwrite
);
...
...
@@ -565,9 +556,6 @@ export class FileService extends Disposable implements IFileService {
const
sourceProvider
=
await
this
.
withReadWriteProvider
(
source
);
const
targetProvider
=
this
.
throwIfFileSystemIsReadonly
(
await
this
.
withReadWriteProvider
(
target
));
// before events
await
this
.
_onWillRunOperation
.
fireAsync
(
promises
=>
new
FileOperationWillRunEvent
(
promises
,
FileOperation
.
COPY
,
target
,
source
));
// copy
const
mode
=
await
this
.
doMoveCopy
(
sourceProvider
,
source
,
targetProvider
,
target
,
'
copy
'
,
!!
overwrite
);
...
...
@@ -722,9 +710,6 @@ export class FileService extends Disposable implements IFileService {
async
createFolder
(
resource
:
URI
):
Promise
<
IFileStatWithMetadata
>
{
const
provider
=
this
.
throwIfFileSystemIsReadonly
(
await
this
.
withProvider
(
resource
));
// before events
await
this
.
_onWillRunOperation
.
fireAsync
(
promises
=>
new
FileOperationWillRunEvent
(
promises
,
FileOperation
.
CREATE
,
resource
));
// mkdir recursively
await
this
.
mkdirp
(
provider
,
resource
);
...
...
@@ -787,9 +772,6 @@ export class FileService extends Disposable implements IFileService {
}
}
// Before Event
await
this
.
_onWillRunOperation
.
fireAsync
(
promises
=>
new
FileOperationWillRunEvent
(
promises
,
FileOperation
.
DELETE
,
resource
));
// Delete through provider
await
provider
.
delete
(
resource
,
{
recursive
,
useTrash
});
...
...
src/vs/platform/files/common/files.ts
浏览文件 @
9f6518c5
...
...
@@ -7,7 +7,7 @@ import { sep } from 'vs/base/common/path';
import
{
URI
}
from
'
vs/base/common/uri
'
;
import
*
as
glob
from
'
vs/base/common/glob
'
;
import
{
createDecorator
}
from
'
vs/platform/instantiation/common/instantiation
'
;
import
{
Event
,
IWaitUntil
}
from
'
vs/base/common/event
'
;
import
{
Event
}
from
'
vs/base/common/event
'
;
import
{
startsWithIgnoreCase
}
from
'
vs/base/common/strings
'
;
import
{
IDisposable
}
from
'
vs/base/common/lifecycle
'
;
import
{
isEqualOrParent
,
isEqual
}
from
'
vs/base/common/resources
'
;
...
...
@@ -57,11 +57,6 @@ export interface IFileService {
*/
readonly
onFileChanges
:
Event
<
FileChangesEvent
>
;
/**
* An event that is fired before attempting a certain file operation.
*/
readonly
onWillRunOperation
:
Event
<
FileOperationWillRunEvent
>
;
/**
* An event that is fired upon successful completion of a certain file operation.
*/
...
...
@@ -377,23 +372,6 @@ export class FileOperationEvent {
}
}
export
class
FileOperationWillRunEvent
implements
IWaitUntil
{
constructor
(
private
_thenables
:
Promise
<
any
>
[],
readonly
operation
:
FileOperation
,
readonly
target
:
URI
,
readonly
source
?:
URI
|
undefined
)
{
}
waitUntil
(
thenable
:
Promise
<
any
>
):
void
{
if
(
Object
.
isFrozen
(
this
.
_thenables
))
{
throw
new
Error
(
'
waitUntil cannot be used aync
'
);
}
this
.
_thenables
.
push
(
thenable
);
}
}
/**
* Possible changes that can occur to a file.
*/
...
...
src/vs/platform/files/test/node/diskFileService.test.ts
浏览文件 @
9f6518c5
...
...
@@ -15,7 +15,7 @@ import { getPathFromAmdModule } from 'vs/base/common/amd';
import
{
copy
,
rimraf
,
symlink
,
RimRafMode
,
rimrafSync
}
from
'
vs/base/node/pfs
'
;
import
{
URI
}
from
'
vs/base/common/uri
'
;
import
{
existsSync
,
statSync
,
readdirSync
,
readFileSync
,
writeFileSync
,
renameSync
,
unlinkSync
,
mkdirSync
,
createReadStream
}
from
'
fs
'
;
import
{
FileOperation
,
FileOperationEvent
,
IFileStat
,
FileOperationResult
,
FileSystemProviderCapabilities
,
FileChangeType
,
IFileChange
,
FileChangesEvent
,
FileOperationError
,
etag
,
IStat
,
IFileStatWithMetadata
,
FileOperationWillRunEvent
}
from
'
vs/platform/files/common/files
'
;
import
{
FileOperation
,
FileOperationEvent
,
IFileStat
,
FileOperationResult
,
FileSystemProviderCapabilities
,
FileChangeType
,
IFileChange
,
FileChangesEvent
,
FileOperationError
,
etag
,
IStat
,
IFileStatWithMetadata
}
from
'
vs/platform/files/common/files
'
;
import
{
NullLogService
}
from
'
vs/platform/log/common/log
'
;
import
{
isLinux
,
isWindows
}
from
'
vs/base/common/platform
'
;
import
{
DisposableStore
}
from
'
vs/base/common/lifecycle
'
;
...
...
@@ -155,9 +155,6 @@ suite('Disk File Service', function () {
});
test
(
'
createFolder
'
,
async
()
=>
{
let
beforeEvent
:
FileOperationWillRunEvent
|
undefined
;
disposables
.
add
(
service
.
onWillRunOperation
(
e
=>
beforeEvent
=
e
));
let
event
:
FileOperationEvent
|
undefined
;
disposables
.
add
(
service
.
onAfterOperation
(
e
=>
event
=
e
));
...
...
@@ -170,11 +167,6 @@ suite('Disk File Service', function () {
assert
.
equal
(
newFolder
.
name
,
'
newFolder
'
);
assert
.
equal
(
existsSync
(
newFolder
.
resource
.
fsPath
),
true
);
assert
.
ok
(
beforeEvent
);
assert
.
equal
(
beforeEvent
!
.
target
.
fsPath
,
newFolderResource
.
fsPath
);
assert
.
equal
(
beforeEvent
!
.
source
,
undefined
);
assert
.
equal
(
beforeEvent
!
.
operation
,
FileOperation
.
CREATE
);
assert
.
ok
(
event
);
assert
.
equal
(
event
!
.
resource
.
fsPath
,
newFolderResource
.
fsPath
);
assert
.
equal
(
event
!
.
operation
,
FileOperation
.
CREATE
);
...
...
@@ -418,9 +410,6 @@ suite('Disk File Service', function () {
});
test
(
'
deleteFile
'
,
async
()
=>
{
let
beforeEvent
:
FileOperationWillRunEvent
|
undefined
;
disposables
.
add
(
service
.
onWillRunOperation
(
e
=>
beforeEvent
=
e
));
let
event
:
FileOperationEvent
;
disposables
.
add
(
service
.
onAfterOperation
(
e
=>
event
=
e
));
...
...
@@ -431,11 +420,6 @@ suite('Disk File Service', function () {
assert
.
equal
(
existsSync
(
source
.
resource
.
fsPath
),
false
);
assert
.
ok
(
beforeEvent
!
);
assert
.
equal
(
beforeEvent
!
.
target
.
fsPath
,
resource
.
fsPath
);
assert
.
equal
(
beforeEvent
!
.
source
,
undefined
);
assert
.
equal
(
beforeEvent
!
.
operation
,
FileOperation
.
DELETE
);
assert
.
ok
(
event
!
);
assert
.
equal
(
event
!
.
resource
.
fsPath
,
resource
.
fsPath
);
assert
.
equal
(
event
!
.
operation
,
FileOperation
.
DELETE
);
...
...
@@ -471,9 +455,6 @@ suite('Disk File Service', function () {
});
test
(
'
move
'
,
async
()
=>
{
let
beforeEvent
:
FileOperationWillRunEvent
|
undefined
;
disposables
.
add
(
service
.
onWillRunOperation
(
e
=>
beforeEvent
=
e
));
let
event
:
FileOperationEvent
;
disposables
.
add
(
service
.
onAfterOperation
(
e
=>
event
=
e
));
...
...
@@ -486,10 +467,6 @@ suite('Disk File Service', function () {
assert
.
equal
(
existsSync
(
renamed
.
resource
.
fsPath
),
true
);
assert
.
equal
(
existsSync
(
source
.
fsPath
),
false
);
assert
.
ok
(
beforeEvent
!
);
assert
.
equal
(
beforeEvent
!
.
operation
,
FileOperation
.
MOVE
);
assert
.
equal
(
beforeEvent
!
.
source
?.
fsPath
,
source
.
fsPath
);
assert
.
equal
(
beforeEvent
!
.
target
?.
fsPath
,
target
.
fsPath
);
assert
.
ok
(
event
!
);
assert
.
equal
(
event
!
.
resource
.
fsPath
,
source
.
fsPath
);
assert
.
equal
(
event
!
.
operation
,
FileOperation
.
MOVE
);
...
...
@@ -844,9 +821,6 @@ suite('Disk File Service', function () {
}
async
function
doTestCopy
(
sourceName
:
string
=
'
index.html
'
)
{
let
beforeEvent
:
FileOperationWillRunEvent
|
undefined
;
disposables
.
add
(
service
.
onWillRunOperation
(
e
=>
beforeEvent
=
e
));
let
event
:
FileOperationEvent
;
disposables
.
add
(
service
.
onAfterOperation
(
e
=>
event
=
e
));
...
...
@@ -857,10 +831,6 @@ suite('Disk File Service', function () {
assert
.
equal
(
existsSync
(
copied
.
resource
.
fsPath
),
true
);
assert
.
equal
(
existsSync
(
source
.
resource
.
fsPath
),
true
);
assert
.
ok
(
beforeEvent
!
);
assert
.
equal
(
beforeEvent
!
.
source
!
.
fsPath
,
source
.
resource
.
fsPath
);
assert
.
equal
(
beforeEvent
!
.
operation
,
FileOperation
.
COPY
);
assert
.
equal
(
beforeEvent
!
.
target
!
.
fsPath
,
copied
.
resource
.
fsPath
);
assert
.
ok
(
event
!
);
assert
.
equal
(
event
!
.
resource
.
fsPath
,
source
.
resource
.
fsPath
);
assert
.
equal
(
event
!
.
operation
,
FileOperation
.
COPY
);
...
...
@@ -1369,9 +1339,6 @@ suite('Disk File Service', function () {
});
async
function
assertCreateFile
(
converter
:
(
content
:
string
)
=>
VSBuffer
|
VSBufferReadable
|
VSBufferReadableStream
):
Promise
<
void
>
{
let
beforeEvent
:
FileOperationWillRunEvent
|
undefined
;
disposables
.
add
(
service
.
onWillRunOperation
(
e
=>
beforeEvent
=
e
));
let
event
:
FileOperationEvent
;
disposables
.
add
(
service
.
onAfterOperation
(
e
=>
event
=
e
));
...
...
@@ -1382,10 +1349,6 @@ suite('Disk File Service', function () {
assert
.
equal
(
existsSync
(
fileStat
.
resource
.
fsPath
),
true
);
assert
.
equal
(
readFileSync
(
fileStat
.
resource
.
fsPath
),
contents
);
assert
.
ok
(
beforeEvent
!
);
assert
.
equal
(
beforeEvent
!
.
target
.
fsPath
,
resource
.
fsPath
);
assert
.
equal
(
beforeEvent
!
.
source
,
undefined
);
assert
.
equal
(
beforeEvent
!
.
operation
,
FileOperation
.
CREATE
);
assert
.
ok
(
event
!
);
assert
.
equal
(
event
!
.
resource
.
fsPath
,
resource
.
fsPath
);
assert
.
equal
(
event
!
.
operation
,
FileOperation
.
CREATE
);
...
...
src/vs/workbench/api/browser/mainThreadFileSystemEventService.ts
浏览文件 @
9f6518c5
...
...
@@ -3,19 +3,21 @@
* Licensed under the MIT License. See License.txt in the project root for license information.
*--------------------------------------------------------------------------------------------*/
import
{
IDisposable
,
dispos
e
}
from
'
vs/base/common/lifecycle
'
;
import
{
DisposableStor
e
}
from
'
vs/base/common/lifecycle
'
;
import
{
FileChangeType
,
IFileService
}
from
'
vs/platform/files/common/files
'
;
import
{
extHostCustomer
}
from
'
vs/workbench/api/common/extHostCustomers
'
;
import
{
ExtHostContext
,
FileSystemEvents
,
IExtHostContext
}
from
'
../common/extHost.protocol
'
;
import
{
ITextFileService
}
from
'
vs/workbench/services/textfile/common/textfiles
'
;
@
extHostCustomer
export
class
MainThreadFileSystemEventService
{
private
readonly
_listener
=
new
Array
<
IDisposable
>
();
private
readonly
_listener
=
new
DisposableStore
();
constructor
(
extHostContext
:
IExtHostContext
,
@
IFileService
fileService
:
IFileService
@
IFileService
fileService
:
IFileService
,
@
ITextFileService
textFileService
:
ITextFileService
)
{
const
proxy
=
extHostContext
.
getProxy
(
ExtHostContext
.
ExtHostFileSystemEventService
);
...
...
@@ -26,7 +28,7 @@ export class MainThreadFileSystemEventService {
changed
:
[],
deleted
:
[]
};
fileService
.
onFileChanges
(
event
=>
{
this
.
_listener
.
add
(
fileService
.
onFileChanges
(
event
=>
{
for
(
let
change
of
event
.
changes
)
{
switch
(
change
.
type
)
{
case
FileChangeType
.
ADDED
:
...
...
@@ -45,14 +47,14 @@ export class MainThreadFileSystemEventService {
events
.
created
.
length
=
0
;
events
.
changed
.
length
=
0
;
events
.
deleted
.
length
=
0
;
}
,
undefined
,
this
.
_listener
);
}
)
);
// file operation events
fileService
.
onWillRunOperation
(
e
=>
proxy
.
$onWillRunFileOperation
(
e
.
operation
,
e
.
target
,
e
.
source
));
fileService
.
onAfterOperation
(
e
=>
proxy
.
$onDidRunFileOperation
(
e
.
operation
,
e
.
resource
,
e
.
target
&&
e
.
target
.
resource
),
undefined
,
this
.
_listener
);
this
.
_listener
.
add
(
textFileService
.
onWillRunOperation
(
e
=>
proxy
.
$onWillRunFileOperation
(
e
.
operation
,
e
.
target
,
e
.
source
)
));
this
.
_listener
.
add
(
textFileService
.
onDidRunOperation
(
e
=>
proxy
.
$onDidRunFileOperation
(
e
.
operation
,
e
.
target
,
e
.
source
))
);
}
dispose
():
void
{
dispose
(
this
.
_listener
);
this
.
_listener
.
dispose
(
);
}
}
src/vs/workbench/services/textfile/browser/textFileService.ts
浏览文件 @
9f6518c5
...
...
@@ -6,14 +6,14 @@
import
*
as
nls
from
'
vs/nls
'
;
import
{
URI
}
from
'
vs/base/common/uri
'
;
import
*
as
objects
from
'
vs/base/common/objects
'
;
import
{
Event
,
Emitter
}
from
'
vs/base/common/event
'
;
import
{
Event
,
Emitter
,
AsyncEmitter
}
from
'
vs/base/common/event
'
;
import
*
as
platform
from
'
vs/base/common/platform
'
;
import
{
IBackupFileService
}
from
'
vs/workbench/services/backup/common/backup
'
;
import
{
IResult
,
ITextFileOperationResult
,
ITextFileService
,
ITextFileStreamContent
,
IAutoSaveConfiguration
,
AutoSaveMode
,
SaveReason
,
ITextFileEditorModelManager
,
ITextFileEditorModel
,
ModelState
,
ISaveOptions
,
AutoSaveContext
,
ITextFileContent
,
IResourceEncodings
,
IReadTextFileOptions
,
IWriteTextFileOptions
,
toBufferOrReadable
,
TextFileOperationError
,
TextFileOperationResult
}
from
'
vs/workbench/services/textfile/common/textfiles
'
;
import
{
IResult
,
ITextFileOperationResult
,
ITextFileService
,
ITextFileStreamContent
,
IAutoSaveConfiguration
,
AutoSaveMode
,
SaveReason
,
ITextFileEditorModelManager
,
ITextFileEditorModel
,
ModelState
,
ISaveOptions
,
AutoSaveContext
,
ITextFileContent
,
IResourceEncodings
,
IReadTextFileOptions
,
IWriteTextFileOptions
,
toBufferOrReadable
,
TextFileOperationError
,
TextFileOperationResult
,
FileOperationWillRunEvent
,
FileOperationDidRunEvent
}
from
'
vs/workbench/services/textfile/common/textfiles
'
;
import
{
ConfirmResult
,
IRevertOptions
}
from
'
vs/workbench/common/editor
'
;
import
{
ILifecycleService
,
ShutdownReason
,
LifecyclePhase
}
from
'
vs/platform/lifecycle/common/lifecycle
'
;
import
{
IWorkspaceContextService
,
WorkbenchState
}
from
'
vs/platform/workspace/common/workspace
'
;
import
{
IFileService
,
IFilesConfiguration
,
FileOperationError
,
FileOperationResult
,
AutoSaveConfiguration
,
HotExitConfiguration
,
IFileStatWithMetadata
,
ICreateFileOptions
}
from
'
vs/platform/files/common/files
'
;
import
{
IFileService
,
IFilesConfiguration
,
FileOperationError
,
FileOperationResult
,
AutoSaveConfiguration
,
HotExitConfiguration
,
IFileStatWithMetadata
,
ICreateFileOptions
,
FileOperation
}
from
'
vs/platform/files/common/files
'
;
import
{
IConfigurationService
}
from
'
vs/platform/configuration/common/configuration
'
;
import
{
Disposable
}
from
'
vs/base/common/lifecycle
'
;
import
{
IWorkbenchEnvironmentService
}
from
'
vs/workbench/services/environment/common/environmentService
'
;
...
...
@@ -52,6 +52,14 @@ export abstract class AbstractTextFileService extends Disposable implements ITex
private
readonly
_onFilesAssociationChange
:
Emitter
<
void
>
=
this
.
_register
(
new
Emitter
<
void
>
());
readonly
onFilesAssociationChange
:
Event
<
void
>
=
this
.
_onFilesAssociationChange
.
event
;
private
_onWillRunOperation
=
this
.
_register
(
new
AsyncEmitter
<
FileOperationWillRunEvent
>
());
readonly
onWillRunOperation
=
this
.
_onWillRunOperation
.
event
;
private
_onDidRunOperation
=
this
.
_register
(
new
Emitter
<
FileOperationDidRunEvent
>
());
readonly
onDidRunOperation
=
this
.
_onDidRunOperation
.
event
;
private
_models
:
TextFileEditorModelManager
;
get
models
():
ITextFileEditorModelManager
{
return
this
.
_models
;
}
...
...
@@ -405,6 +413,10 @@ export abstract class AbstractTextFileService extends Disposable implements ITex
}
async
create
(
resource
:
URI
,
value
?:
string
|
ITextSnapshot
,
options
?:
ICreateFileOptions
):
Promise
<
IFileStatWithMetadata
>
{
// before event
await
this
.
_onWillRunOperation
.
fireAsync
(
promises
=>
new
FileOperationWillRunEvent
(
promises
,
FileOperation
.
CREATE
,
resource
));
const
stat
=
await
this
.
doCreate
(
resource
,
value
,
options
);
// If we had an existing model for the given resource, load
...
...
@@ -416,6 +428,9 @@ export abstract class AbstractTextFileService extends Disposable implements ITex
await
existingModel
.
revert
();
}
// after event
this
.
_onDidRunOperation
.
fire
(
new
FileOperationDidRunEvent
(
FileOperation
.
CREATE
,
resource
));
return
stat
;
}
...
...
@@ -428,15 +443,21 @@ export abstract class AbstractTextFileService extends Disposable implements ITex
}
async
delete
(
resource
:
URI
,
options
?:
{
useTrash
?:
boolean
,
recursive
?:
boolean
}):
Promise
<
void
>
{
const
dirtyFiles
=
this
.
getDirty
().
filter
(
dirty
=>
isEqualOrParent
(
dirty
,
resource
));
await
this
.
_onWillRunOperation
.
fireAsync
(
promises
=>
new
FileOperationWillRunEvent
(
promises
,
FileOperation
.
DELETE
,
resource
));
const
dirtyFiles
=
this
.
getDirty
().
filter
(
dirty
=>
isEqualOrParent
(
dirty
,
resource
));
await
this
.
revertAll
(
dirtyFiles
,
{
soft
:
true
});
return
this
.
fileService
.
del
(
resource
,
options
);
await
this
.
fileService
.
del
(
resource
,
options
);
this
.
_onDidRunOperation
.
fire
(
new
FileOperationDidRunEvent
(
FileOperation
.
DELETE
,
resource
));
}
async
move
(
source
:
URI
,
target
:
URI
,
overwrite
?:
boolean
):
Promise
<
IFileStatWithMetadata
>
{
// before events
await
this
.
_onWillRunOperation
.
fireAsync
(
promises
=>
new
FileOperationWillRunEvent
(
promises
,
FileOperation
.
MOVE
,
target
,
source
));
// find all models that related to either source or target (can be many if resource is a folder)
const
sourceModels
:
ITextFileEditorModel
[]
=
[];
const
conflictingModels
:
ITextFileEditorModel
[]
=
[];
...
...
@@ -514,6 +535,9 @@ export abstract class AbstractTextFileService extends Disposable implements ITex
}
}));
// after event
this
.
_onDidRunOperation
.
fire
(
new
FileOperationDidRunEvent
(
FileOperation
.
MOVE
,
target
,
source
));
return
stat
;
}
...
...
src/vs/workbench/services/textfile/common/textfiles.ts
浏览文件 @
9f6518c5
...
...
@@ -4,10 +4,10 @@
*--------------------------------------------------------------------------------------------*/
import
{
URI
}
from
'
vs/base/common/uri
'
;
import
{
Event
}
from
'
vs/base/common/event
'
;
import
{
Event
,
IWaitUntil
}
from
'
vs/base/common/event
'
;
import
{
IDisposable
}
from
'
vs/base/common/lifecycle
'
;
import
{
IEncodingSupport
,
ConfirmResult
,
IRevertOptions
,
IModeSupport
}
from
'
vs/workbench/common/editor
'
;
import
{
IBaseStatWithMetadata
,
IFileStatWithMetadata
,
IReadFileOptions
,
IWriteFileOptions
,
FileOperationError
,
FileOperationResult
}
from
'
vs/platform/files/common/files
'
;
import
{
IBaseStatWithMetadata
,
IFileStatWithMetadata
,
IReadFileOptions
,
IWriteFileOptions
,
FileOperationError
,
FileOperationResult
,
FileOperation
}
from
'
vs/platform/files/common/files
'
;
import
{
createDecorator
}
from
'
vs/platform/instantiation/common/instantiation
'
;
import
{
ITextEditorModel
}
from
'
vs/editor/common/services/resolverService
'
;
import
{
ITextBufferFactory
,
ITextModel
,
ITextSnapshot
}
from
'
vs/editor/common/model
'
;
...
...
@@ -28,6 +28,16 @@ export interface ITextFileService extends IDisposable {
readonly
isHotExitEnabled
:
boolean
;
/**
* An event that is fired before attempting a certain file operation.
*/
readonly
onWillRunOperation
:
Event
<
FileOperationWillRunEvent
>
;
/**
* An event that is fired after a file operation has been performed.
*/
readonly
onDidRunOperation
:
Event
<
FileOperationDidRunEvent
>
;
/**
* Access to the manager of text file editor models providing further methods to work with them.
*/
...
...
@@ -145,6 +155,35 @@ export interface ITextFileService extends IDisposable {
getAutoSaveConfiguration
():
IAutoSaveConfiguration
;
}
export
class
FileOperationWillRunEvent
implements
IWaitUntil
{
constructor
(
private
_thenables
:
Promise
<
any
>
[],
readonly
operation
:
FileOperation
,
readonly
target
:
URI
,
readonly
source
?:
URI
|
undefined
)
{
}
waitUntil
(
thenable
:
Promise
<
any
>
):
void
{
if
(
Object
.
isFrozen
(
this
.
_thenables
))
{
throw
new
Error
(
'
waitUntil cannot be used aync
'
);
}
this
.
_thenables
.
push
(
thenable
);
}
}
export
class
FileOperationDidRunEvent
{
constructor
(
readonly
operation
:
FileOperation
,
readonly
target
:
URI
,
readonly
source
?:
URI
|
undefined
)
{
}
}
export
interface
IReadTextFileOptions
extends
IReadFileOptions
{
/**
...
...
src/vs/workbench/test/workbenchTestServices.ts
浏览文件 @
9f6518c5
...
...
@@ -923,8 +923,6 @@ export class TestFileService implements IFileService {
public
_serviceBrand
:
undefined
;
readonly
onWillRunOperation
=
Event
.
None
;
private
readonly
_onFileChanges
:
Emitter
<
FileChangesEvent
>
;
private
readonly
_onAfterOperation
:
Emitter
<
FileOperationEvent
>
;
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录