Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
掘金者说
vscode
提交
5ef5837c
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,发现更多精彩内容 >>
提交
5ef5837c
编写于
7月 09, 2021
作者:
E
Eric Amodio
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
Improves Git security with untrusted workspaces
上级
5b8ce768
变更
3
隐藏空白更改
内联
并排
Showing
3 changed file
with
78 addition
and
37 deletion
+78
-37
extensions/git/src/git.ts
extensions/git/src/git.ts
+23
-21
extensions/git/src/main.ts
extensions/git/src/main.ts
+24
-2
extensions/git/src/model.ts
extensions/git/src/model.ts
+31
-14
未找到文件。
extensions/git/src/git.ts
浏览文件 @
5ef5837c
...
@@ -63,9 +63,11 @@ function parseVersion(raw: string): string {
...
@@ -63,9 +63,11 @@ function parseVersion(raw: string): string {
return
raw
.
replace
(
/^git version /
,
''
);
return
raw
.
replace
(
/^git version /
,
''
);
}
}
function
findSpecificGit
(
path
:
string
,
on
Lookup
:
(
path
:
string
)
=>
void
):
Promise
<
IGit
>
{
function
findSpecificGit
(
path
:
string
,
on
Validate
:
(
path
:
string
)
=>
boolean
):
Promise
<
IGit
>
{
return
new
Promise
<
IGit
>
((
c
,
e
)
=>
{
return
new
Promise
<
IGit
>
((
c
,
e
)
=>
{
onLookup
(
path
);
if
(
!
onValidate
(
path
))
{
return
e
(
'
git not found
'
);
}
const
buffers
:
Buffer
[]
=
[];
const
buffers
:
Buffer
[]
=
[];
const
child
=
cp
.
spawn
(
path
,
[
'
--version
'
]);
const
child
=
cp
.
spawn
(
path
,
[
'
--version
'
]);
...
@@ -75,7 +77,7 @@ function findSpecificGit(path: string, onLookup: (path: string) => void): Promis
...
@@ -75,7 +77,7 @@ function findSpecificGit(path: string, onLookup: (path: string) => void): Promis
});
});
}
}
function
findGitDarwin
(
on
Lookup
:
(
path
:
string
)
=>
void
):
Promise
<
IGit
>
{
function
findGitDarwin
(
on
Validate
:
(
path
:
string
)
=>
boolean
):
Promise
<
IGit
>
{
return
new
Promise
<
IGit
>
((
c
,
e
)
=>
{
return
new
Promise
<
IGit
>
((
c
,
e
)
=>
{
cp
.
exec
(
'
which git
'
,
(
err
,
gitPathBuffer
)
=>
{
cp
.
exec
(
'
which git
'
,
(
err
,
gitPathBuffer
)
=>
{
if
(
err
)
{
if
(
err
)
{
...
@@ -85,7 +87,9 @@ function findGitDarwin(onLookup: (path: string) => void): Promise<IGit> {
...
@@ -85,7 +87,9 @@ function findGitDarwin(onLookup: (path: string) => void): Promise<IGit> {
const
path
=
gitPathBuffer
.
toString
().
replace
(
/^
\s
+|
\s
+$/g
,
''
);
const
path
=
gitPathBuffer
.
toString
().
replace
(
/^
\s
+|
\s
+$/g
,
''
);
function
getVersion
(
path
:
string
)
{
function
getVersion
(
path
:
string
)
{
onLookup
(
path
);
if
(
!
onValidate
(
path
))
{
return
e
(
'
git not found
'
);
}
// make sure git executes
// make sure git executes
cp
.
exec
(
'
git --version
'
,
(
err
,
stdout
)
=>
{
cp
.
exec
(
'
git --version
'
,
(
err
,
stdout
)
=>
{
...
@@ -117,33 +121,31 @@ function findGitDarwin(onLookup: (path: string) => void): Promise<IGit> {
...
@@ -117,33 +121,31 @@ function findGitDarwin(onLookup: (path: string) => void): Promise<IGit> {
});
});
}
}
function
findSystemGitWin32
(
base
:
string
,
on
Lookup
:
(
path
:
string
)
=>
void
):
Promise
<
IGit
>
{
function
findSystemGitWin32
(
base
:
string
,
on
Validate
:
(
path
:
string
)
=>
boolean
):
Promise
<
IGit
>
{
if
(
!
base
)
{
if
(
!
base
)
{
return
Promise
.
reject
<
IGit
>
(
'
Not found
'
);
return
Promise
.
reject
<
IGit
>
(
'
Not found
'
);
}
}
return
findSpecificGit
(
path
.
join
(
base
,
'
Git
'
,
'
cmd
'
,
'
git.exe
'
),
on
Lookup
);
return
findSpecificGit
(
path
.
join
(
base
,
'
Git
'
,
'
cmd
'
,
'
git.exe
'
),
on
Validate
);
}
}
function
findGitWin32InPath
(
on
Lookup
:
(
path
:
string
)
=>
void
):
Promise
<
IGit
>
{
function
findGitWin32InPath
(
on
Validate
:
(
path
:
string
)
=>
boolean
):
Promise
<
IGit
>
{
const
whichPromise
=
new
Promise
<
string
>
((
c
,
e
)
=>
which
(
'
git.exe
'
,
(
err
,
path
)
=>
err
?
e
(
err
)
:
c
(
path
)));
const
whichPromise
=
new
Promise
<
string
>
((
c
,
e
)
=>
which
(
'
git.exe
'
,
(
err
,
path
)
=>
err
?
e
(
err
)
:
c
(
path
)));
return
whichPromise
.
then
(
path
=>
findSpecificGit
(
path
,
on
Lookup
));
return
whichPromise
.
then
(
path
=>
findSpecificGit
(
path
,
on
Validate
));
}
}
function
findGitWin32
(
on
Lookup
:
(
path
:
string
)
=>
void
):
Promise
<
IGit
>
{
function
findGitWin32
(
on
Validate
:
(
path
:
string
)
=>
boolean
):
Promise
<
IGit
>
{
return
findSystemGitWin32
(
process
.
env
[
'
ProgramW6432
'
]
as
string
,
on
Lookup
)
return
findSystemGitWin32
(
process
.
env
[
'
ProgramW6432
'
]
as
string
,
on
Validate
)
.
then
(
undefined
,
()
=>
findSystemGitWin32
(
process
.
env
[
'
ProgramFiles(x86)
'
]
as
string
,
on
Lookup
))
.
then
(
undefined
,
()
=>
findSystemGitWin32
(
process
.
env
[
'
ProgramFiles(x86)
'
]
as
string
,
on
Validate
))
.
then
(
undefined
,
()
=>
findSystemGitWin32
(
process
.
env
[
'
ProgramFiles
'
]
as
string
,
on
Lookup
))
.
then
(
undefined
,
()
=>
findSystemGitWin32
(
process
.
env
[
'
ProgramFiles
'
]
as
string
,
on
Validate
))
.
then
(
undefined
,
()
=>
findSystemGitWin32
(
path
.
join
(
process
.
env
[
'
LocalAppData
'
]
as
string
,
'
Programs
'
),
on
Lookup
))
.
then
(
undefined
,
()
=>
findSystemGitWin32
(
path
.
join
(
process
.
env
[
'
LocalAppData
'
]
as
string
,
'
Programs
'
),
on
Validate
))
.
then
(
undefined
,
()
=>
findGitWin32InPath
(
on
Lookup
));
.
then
(
undefined
,
()
=>
findGitWin32InPath
(
on
Validate
));
}
}
export
async
function
findGit
(
hint
:
string
|
string
[]
|
undefined
,
onLookup
:
(
path
:
string
)
=>
void
):
Promise
<
IGit
>
{
export
async
function
findGit
(
hints
:
string
[],
onValidate
:
(
path
:
string
)
=>
boolean
):
Promise
<
IGit
>
{
const
hints
=
Array
.
isArray
(
hint
)
?
hint
:
hint
?
[
hint
]
:
[];
for
(
const
hint
of
hints
)
{
for
(
const
hint
of
hints
)
{
try
{
try
{
return
await
findSpecificGit
(
hint
,
on
Lookup
);
return
await
findSpecificGit
(
hint
,
on
Validate
);
}
catch
{
}
catch
{
// noop
// noop
}
}
...
@@ -151,9 +153,9 @@ export async function findGit(hint: string | string[] | undefined, onLookup: (pa
...
@@ -151,9 +153,9 @@ export async function findGit(hint: string | string[] | undefined, onLookup: (pa
try
{
try
{
switch
(
process
.
platform
)
{
switch
(
process
.
platform
)
{
case
'
darwin
'
:
return
await
findGitDarwin
(
on
Lookup
);
case
'
darwin
'
:
return
await
findGitDarwin
(
on
Validate
);
case
'
win32
'
:
return
await
findGitWin32
(
on
Lookup
);
case
'
win32
'
:
return
await
findGitWin32
(
on
Validate
);
default
:
return
await
findSpecificGit
(
'
git
'
,
on
Lookup
);
default
:
return
await
findSpecificGit
(
'
git
'
,
on
Validate
);
}
}
}
catch
{
}
catch
{
// noop
// noop
...
...
extensions/git/src/main.ts
浏览文件 @
5ef5837c
...
@@ -34,8 +34,30 @@ export async function deactivate(): Promise<any> {
...
@@ -34,8 +34,30 @@ export async function deactivate(): Promise<any> {
}
}
async
function
createModel
(
context
:
ExtensionContext
,
outputChannel
:
OutputChannel
,
telemetryReporter
:
TelemetryReporter
,
disposables
:
Disposable
[]):
Promise
<
Model
>
{
async
function
createModel
(
context
:
ExtensionContext
,
outputChannel
:
OutputChannel
,
telemetryReporter
:
TelemetryReporter
,
disposables
:
Disposable
[]):
Promise
<
Model
>
{
const
pathHint
=
workspace
.
getConfiguration
(
'
git
'
).
get
<
string
|
string
[]
>
(
'
path
'
);
const
pathValue
=
workspace
.
getConfiguration
(
'
git
'
).
get
<
string
|
string
[]
>
(
'
path
'
);
const
info
=
await
findGit
(
pathHint
,
path
=>
outputChannel
.
appendLine
(
localize
(
'
looking
'
,
"
Looking for git in: {0}
"
,
path
)));
let
pathHints
=
Array
.
isArray
(
pathValue
)
?
pathValue
:
pathValue
?
[
pathValue
]
:
[];
const
{
isTrusted
,
workspaceFolders
=
[]
}
=
workspace
;
const
excludes
=
isTrusted
?
[]
:
workspaceFolders
.
map
(
f
=>
path
.
normalize
(
f
.
uri
.
fsPath
).
replace
(
/
[\r\n]
+$/
,
''
));
if
(
!
isTrusted
&&
pathHints
.
length
!==
0
)
{
// Filter out any non-absolute paths
pathHints
=
pathHints
.
filter
(
p
=>
path
.
isAbsolute
(
p
));
}
const
info
=
await
findGit
(
pathHints
,
gitPath
=>
{
outputChannel
.
appendLine
(
localize
(
'
validating
'
,
"
Validating found git in: {0}
"
,
gitPath
));
if
(
excludes
.
length
===
0
)
{
return
true
;
}
const
normalized
=
path
.
normalize
(
gitPath
).
replace
(
/
[\r\n]
+$/
,
''
);
const
skip
=
excludes
.
some
(
e
=>
normalized
.
startsWith
(
e
));
if
(
skip
)
{
outputChannel
.
appendLine
(
localize
(
'
skipped
'
,
"
Skipped found git in: {0}
"
,
gitPath
));
}
return
!
skip
;
});
const
askpass
=
await
Askpass
.
create
(
outputChannel
,
context
.
storagePath
);
const
askpass
=
await
Askpass
.
create
(
outputChannel
,
context
.
storagePath
);
disposables
.
push
(
askpass
);
disposables
.
push
(
askpass
);
...
...
extensions/git/src/model.ts
浏览文件 @
5ef5837c
...
@@ -147,23 +147,23 @@ export class Model implements IRemoteSourceProviderRegistry, IPushErrorHandlerRe
...
@@ -147,23 +147,23 @@ export class Model implements IRemoteSourceProviderRegistry, IPushErrorHandlerRe
await
Promise
.
all
((
workspace
.
workspaceFolders
||
[]).
map
(
async
folder
=>
{
await
Promise
.
all
((
workspace
.
workspaceFolders
||
[]).
map
(
async
folder
=>
{
const
root
=
folder
.
uri
.
fsPath
;
const
root
=
folder
.
uri
.
fsPath
;
const
children
=
await
new
Promise
<
string
[]
>
((
c
,
e
)
=>
fs
.
readdir
(
root
,
(
err
,
r
)
=>
err
?
e
(
err
)
:
c
(
r
)));
const
children
=
await
new
Promise
<
string
[]
>
((
c
,
e
)
=>
fs
.
readdir
(
root
,
(
err
,
r
)
=>
err
?
e
(
err
)
:
c
(
r
)));
const
promises
=
children
const
subfolders
=
new
Set
(
children
.
filter
(
child
=>
child
!==
'
.git
'
).
map
(
child
=>
path
.
join
(
root
,
child
)));
.
filter
(
child
=>
child
!==
'
.git
'
)
.
map
(
child
=>
this
.
openRepository
(
path
.
join
(
root
,
child
)));
const
folderConfig
=
workspace
.
getConfiguration
(
'
git
'
,
folder
.
uri
);
const
scanPaths
=
(
workspace
.
isTrusted
?
workspace
.
getConfiguration
(
'
git
'
,
folder
.
uri
)
:
config
).
get
<
string
[]
>
(
'
scanRepositories
'
)
||
[];
const
paths
=
folderConfig
.
get
<
string
[]
>
(
'
scanRepositories
'
)
||
[];
for
(
const
scanPath
of
scanPaths
)
{
if
(
scanPath
!==
'
.git
'
)
{
continue
;
}
for
(
const
possibleRepositoryPath
of
paths
)
{
if
(
path
.
isAbsolute
(
scanPath
))
{
if
(
path
.
isAbsolute
(
possibleRepositoryPath
))
{
console
.
warn
(
localize
(
'
not supported
'
,
"
Absolute paths not supported in 'git.scanRepositories' setting.
"
));
console
.
warn
(
localize
(
'
not supported
'
,
"
Absolute paths not supported in 'git.scanRepositories' setting.
"
));
continue
;
continue
;
}
}
promises
.
push
(
this
.
openRepository
(
path
.
join
(
root
,
possibleRepositoryPath
)
));
subfolders
.
add
(
path
.
join
(
root
,
scanPath
));
}
}
await
Promise
.
all
(
promises
);
await
Promise
.
all
(
[...
subfolders
].
map
(
f
=>
this
.
openRepository
(
f
))
);
}));
}));
}
}
...
@@ -226,6 +226,10 @@ export class Model implements IRemoteSourceProviderRegistry, IPushErrorHandlerRe
...
@@ -226,6 +226,10 @@ export class Model implements IRemoteSourceProviderRegistry, IPushErrorHandlerRe
}
}
private
async
onDidChangeVisibleTextEditors
(
editors
:
readonly
TextEditor
[]):
Promise
<
void
>
{
private
async
onDidChangeVisibleTextEditors
(
editors
:
readonly
TextEditor
[]):
Promise
<
void
>
{
if
(
!
workspace
.
isTrusted
)
{
return
;
}
const
config
=
workspace
.
getConfiguration
(
'
git
'
);
const
config
=
workspace
.
getConfiguration
(
'
git
'
);
const
autoRepositoryDetection
=
config
.
get
<
boolean
|
'
subFolders
'
|
'
openEditors
'
>
(
'
autoRepositoryDetection
'
);
const
autoRepositoryDetection
=
config
.
get
<
boolean
|
'
subFolders
'
|
'
openEditors
'
>
(
'
autoRepositoryDetection
'
);
...
@@ -251,20 +255,33 @@ export class Model implements IRemoteSourceProviderRegistry, IPushErrorHandlerRe
...
@@ -251,20 +255,33 @@ export class Model implements IRemoteSourceProviderRegistry, IPushErrorHandlerRe
}
}
@
sequentialize
@
sequentialize
async
openRepository
(
p
ath
:
string
):
Promise
<
void
>
{
async
openRepository
(
repoP
ath
:
string
):
Promise
<
void
>
{
if
(
this
.
getRepository
(
p
ath
))
{
if
(
this
.
getRepository
(
repoP
ath
))
{
return
;
return
;
}
}
const
config
=
workspace
.
getConfiguration
(
'
git
'
,
Uri
.
file
(
p
ath
));
const
config
=
workspace
.
getConfiguration
(
'
git
'
,
Uri
.
file
(
repoP
ath
));
const
enabled
=
config
.
get
<
boolean
>
(
'
enabled
'
)
===
true
;
const
enabled
=
config
.
get
<
boolean
>
(
'
enabled
'
)
===
true
;
if
(
!
enabled
)
{
if
(
!
enabled
)
{
return
;
return
;
}
}
if
(
!
workspace
.
isTrusted
)
{
// Check if the folder is a bare repo: if it has a file named HEAD && `rev-parse --show -cdup` is empty
try
{
fs
.
accessSync
(
path
.
join
(
repoPath
,
'
HEAD
'
),
fs
.
constants
.
F_OK
);
const
result
=
await
this
.
git
.
exec
(
repoPath
,
[
'
-C
'
,
repoPath
,
'
rev-parse
'
,
'
--show-cdup
'
],
{
log
:
false
});
if
(
result
.
stderr
.
trim
()
===
''
&&
result
.
stdout
.
trim
()
===
''
)
{
return
;
}
}
catch
{
// If this throw, we should be good to open the repo (e.g. HEAD doesn't exist)
}
}
try
{
try
{
const
rawRoot
=
await
this
.
git
.
getRepositoryRoot
(
p
ath
);
const
rawRoot
=
await
this
.
git
.
getRepositoryRoot
(
repoP
ath
);
// This can happen whenever `path` has the wrong case sensitivity in
// This can happen whenever `path` has the wrong case sensitivity in
// case insensitive file systems
// case insensitive file systems
...
@@ -286,7 +303,7 @@ export class Model implements IRemoteSourceProviderRegistry, IPushErrorHandlerRe
...
@@ -286,7 +303,7 @@ export class Model implements IRemoteSourceProviderRegistry, IPushErrorHandlerRe
await
repository
.
status
();
await
repository
.
status
();
}
catch
(
ex
)
{
}
catch
(
ex
)
{
// noop
// noop
this
.
outputChannel
.
appendLine
(
`Opening repository for path='
${
p
ath
}
' failed; ex=
${
ex
}
`
);
this
.
outputChannel
.
appendLine
(
`Opening repository for path='
${
repoP
ath
}
' failed; ex=
${
ex
}
`
);
}
}
}
}
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录