更新我的问题:
我有以下三个功能:
func IsSymlinks(path string) {
...
...
}
func (c *MyClass) myFunc1(path string) {
...more code
...more code
if IsSymlinks(path) {
realPath := filepath.EvalSymlinks(path)
}
...more code
...more code
}
func myFunc2(path string) {
...more code
...more code
if IsSymlinks(path) {
realPath := filepath.EvalSymlinks(path)
}
...more code
...more code
}
我的问题是如何通过模拟filepath.EvalSymlinks和IsSymlinks测试myFunc1和myFunc2?我搜索了一些帖子,并看到了几种解决方案。
创建一个函数类型为EvalSymlinks的变量,并使用filepath.EvalSymlinks进行初始化,然后在测试包中将其更改为我的实现。但是,我不想使用这种方法。
将文件路径.EvalSymlinks和IsSymlinks传递给myFunc作为参数。我也不想使用这种方式。
很多人都在谈论模拟使用界面。能否请你帮忙?还是可以测试myFunc的另一种方法?谢谢!
我在考虑的另一种选择是,在执行功能测试之前,在os中创建到路径的符号链接,然后在测试之后立即删除符号链接是否是一种好习惯?
答案 0 :(得分:1)
您可以通过使用界面来实现。例如,假设您有一个名为Linker的接口:
type Linker interface {
IsSymlinks(path String)
}
现在,您可以将链接器对象嵌入到调用IsSymlinks
方法的函数中。
type MyClass struct {
Linker
}
func (p *MyClass) myFunc(path String) {
_ = p.Linker.IsSymlinks(path)
}
现在,您可以在测试中创建一个模拟链接器。
type mockLinker struct{}
//implement the IsSymlinks on the mockLinker as you wish
p := &MyClass{
Linker: mockLinker,
}
p.myFunc(path)
当p.myFunc
到达IsSymlinks
方法时,它将调用您的模拟IsSymlinks
方法。
对于filepath.EvalSymlinks(path)
,您可以将该方法包装在您自己的另一个方法中,然后将新方法添加到同一接口中并模拟该方法,而不是模拟EvalSymlinks
。
仅出于测试目的而创建接口可能并不总是最好的主意,因为在某些情况下,可能会导致在Go中不习惯使用大型接口,因为这会使代码的可读性降低。
答案 1 :(得分:0)
我认为您可以尝试以其他方式设计MyClass结构和相关功能。我的意思是从文件路径之类的包中获得独立的MyClass对象。首先,创建一个具有两个功能的新界面:
type MyEvalLink interface {
IsSymlinks(path string) bool
EvalSymlinks(path string) (string, error)
}
然后,您可以在使用文件路径包或伪代码的结构中实现这两个功能:
type EvalLinkUse struct{}
func (p *EvalLinkUse) IsSymlinks(path string) bool {
// put here your real code or fake
}
func (p *EvalLinkUse) EvalSymlinks(path string) (string, error) {
// put here your real code or fake
}
因此,您的代码将更改如下:
type MyClass struct {
...your code
MyEvalLink MyEvalLink
}
func (c *MyClass) myFunc1(path string) {
...more code
...more code
if c.MyEvalLink.IsSymlinks(path) {
realPath := c.MyEvalLink.EvalSymlinks(path)
}
...more code
...more code
}
适合您的情况吗?