以Go語言表示架構外層(outer layer)與內層(inner layer)的資料傳遞。
本篇是在看簡潔架構(The Clean Architecture)的依賴原則(Dependency Rule)時,以及參考The Clean Architecture — Beginner’s Guides這篇文章後,試著用Go來實現一般依賴、介面隔離和依賴反轉,以及層與層之間資料傳輸物件的擺放位置。
資料傳輸物件要定義在被依賴的那層。
內層為Inner
,外層調用其方法時,透過輸入參數InnerInput
和輸出參數InnerOutput
與外層溝通。輸出/輸入參數即為無操作行為的資料傳輸物件(DTO(Data Transfer Object))。
inner/inner.go
package inner
type Inner struct {
}
type InnerInput struct {
Id string
}
type InnerOutput struct {
Id string
}
func (inner Inner) Do(input InnerInput) InnerOutput {
return InnerOutput{
Id: input.Id,
}
}
外層為Outer
,其依賴內層Inner
,透過內層的輸入參數InnerInput
和輸出參數InnerOutput
來調用內層的方法。
同樣地,外層也有與外界溝通的輸入參數OuterInput
和輸出參數OuterOutput
。
outer/outer.go
package outer
import "abc.com/demo/inner"
type Outer struct {
inner inner.Inner
}
type OuterInput struct {
Id string
}
type OuterOutput struct {
Id string
}
func (outer Outer) Do(input OuterInput) OuterOutput {
innerOutput := outer.inner.Do(
inner.InnerInput{
Id: input.Id,
},
)
return OuterOutput{
Id: innerOutput.Id,
}
}
外層物件依賴內層物件,所以外層為依賴方、內層為被依賴方,所以外層與內層溝通用的資料傳輸物件是定義在內層。
介面隔離、依賴反轉
透過在外層定義介面並讓內層實作該介面,將原本外層依賴內層的關係反轉為內層依賴外層,即依賴反轉。
定義外層使用內層的介面Inner
和方法簽章。
outer/interface.go
package outer
type InnerInput struct {
Id string
}
type InnerOutput struct {
Id string
}
type Inner interface {
Do(input InnerInput) InnerOutput
}
把外層原本依賴的內層改為依賴外層自己的介面,則從此外層不再依賴於內層。
outer/outer.go
package outer
type Outer struct {
inner Inner
}
type OuterInput struct {
Id string
}
type OuterOutput struct {
Id string
}
func (outer Outer) Do(input OuterInput) OuterOutput {
innerOutput := outer.inner.Do(
InnerInput{
Id: input.Id,
},
)
return OuterOutput{
Id: innerOutput.Id,
}
}
內層實作外層介面,也就是內層變成依賴於外層。
inner/inner.go
package inner
import "abc.com/demo/outer"
type Inner struct {
}
type InnerInput struct {
Id string
}
type InnerOutput struct {
Id string
}
func (inner Inner) Do(input outer.InnerInput) outer.InnerOutput {
return outer.InnerOutput{
Id: input.Id,
}
}
沒有留言:
張貼留言