You can not select more than 25 topics Topics must start with a chinese character,a letter or number, can include dashes ('-') and can be up to 35 characters long.

clone.go 3.2 kB

1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140
  1. package ops2
  2. import (
  3. "fmt"
  4. "io"
  5. "github.com/samber/lo"
  6. "gitlink.org.cn/cloudream/common/pkgs/ioswitch/dag"
  7. "gitlink.org.cn/cloudream/common/pkgs/ioswitch/exec"
  8. "gitlink.org.cn/cloudream/common/pkgs/ioswitch/utils"
  9. "gitlink.org.cn/cloudream/common/utils/io2"
  10. "golang.org/x/sync/semaphore"
  11. )
  12. func init() {
  13. exec.UseOp[*CloneStream]()
  14. exec.UseOp[*CloneVar]()
  15. }
  16. type CloneStream struct {
  17. Raw exec.VarID `json:"raw"`
  18. Cloneds []exec.VarID `json:"cloneds"`
  19. }
  20. func (o *CloneStream) Execute(ctx *exec.ExecContext, e *exec.Executor) error {
  21. raw, err := exec.BindVar[*exec.StreamValue](e, ctx.Context, o.Raw)
  22. if err != nil {
  23. return err
  24. }
  25. defer raw.Stream.Close()
  26. cloned := io2.Clone(raw.Stream, len(o.Cloneds))
  27. sem := semaphore.NewWeighted(int64(len(o.Cloneds)))
  28. for i, s := range cloned {
  29. sem.Acquire(ctx.Context, 1)
  30. e.PutVar(o.Cloneds[i], &exec.StreamValue{
  31. Stream: io2.AfterReadClosedOnce(s, func(closer io.ReadCloser) {
  32. sem.Release(1)
  33. }),
  34. })
  35. }
  36. return sem.Acquire(ctx.Context, int64(len(o.Cloneds)))
  37. }
  38. func (o *CloneStream) String() string {
  39. return fmt.Sprintf("CloneStream %v -> (%v)", o.Raw, utils.FormatVarIDs(o.Cloneds))
  40. }
  41. type CloneVar struct {
  42. Raw exec.VarID `json:"raw"`
  43. Cloneds []exec.VarID `json:"cloneds"`
  44. }
  45. func (o *CloneVar) Execute(ctx *exec.ExecContext, e *exec.Executor) error {
  46. raw, err := e.BindVar(ctx.Context, o.Raw)
  47. if err != nil {
  48. return err
  49. }
  50. for i := range o.Cloneds {
  51. e.PutVar(o.Cloneds[i], raw.Clone())
  52. }
  53. return nil
  54. }
  55. func (o *CloneVar) String() string {
  56. return fmt.Sprintf("CloneStream %v -> (%v)", o.Raw, utils.FormatVarIDs(o.Cloneds))
  57. }
  58. type CloneStreamType struct {
  59. dag.NodeBase
  60. }
  61. func (b *GraphNodeBuilder) NewCloneStream() *CloneStreamType {
  62. node := &CloneStreamType{}
  63. b.AddNode(node)
  64. return node
  65. }
  66. func (t *CloneStreamType) SetInput(raw *dag.Var) {
  67. t.InputStreams().EnsureSize(1)
  68. raw.Connect(t, 0)
  69. }
  70. func (t *CloneStreamType) NewOutput() *dag.Var {
  71. output := t.Graph().NewVar()
  72. t.OutputStreams().SetupNew(t, output)
  73. return output
  74. }
  75. func (t *CloneStreamType) GenerateOp() (exec.Op, error) {
  76. return &CloneStream{
  77. Raw: t.InputStreams().Get(0).VarID,
  78. Cloneds: lo.Map(t.OutputStreams().RawArray(), func(v *dag.Var, idx int) exec.VarID {
  79. return v.VarID
  80. }),
  81. }, nil
  82. }
  83. // func (t *CloneStreamType) String() string {
  84. // return fmt.Sprintf("CloneStream[]%v%v", formatStreamIO(node), formatValueIO(node))
  85. // }
  86. type CloneVarType struct {
  87. dag.NodeBase
  88. }
  89. func (b *GraphNodeBuilder) NewCloneValue() *CloneVarType {
  90. node := &CloneVarType{}
  91. b.AddNode(node)
  92. return node
  93. }
  94. func (t *CloneVarType) SetInput(raw *dag.Var) {
  95. t.InputValues().EnsureSize(1)
  96. raw.Connect(t, 0)
  97. }
  98. func (t *CloneVarType) NewOutput() *dag.Var {
  99. output := t.Graph().NewVar()
  100. t.OutputValues().SetupNew(t, output)
  101. return output
  102. }
  103. func (t *CloneVarType) GenerateOp() (exec.Op, error) {
  104. return &CloneVar{
  105. Raw: t.InputValues().Get(0).VarID,
  106. Cloneds: lo.Map(t.OutputValues().RawArray(), func(v *dag.Var, idx int) exec.VarID {
  107. return v.VarID
  108. }),
  109. }, nil
  110. }
  111. // func (t *CloneVarType) String() string {
  112. // return fmt.Sprintf("CloneVar[]%v%v", formatStreamIO(node), formatValueIO(node))
  113. // }

本项目旨在将云际存储公共基础设施化,使个人及企业可低门槛使用高效的云际存储服务(安装开箱即用云际存储客户端即可,无需关注其他组件的部署),同时支持用户灵活便捷定制云际存储的功能细节。