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.

sync.go 2.8 kB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142
  1. package ops
  2. import (
  3. "context"
  4. "fmt"
  5. "io"
  6. "gitlink.org.cn/cloudream/common/pkgs/future"
  7. "gitlink.org.cn/cloudream/storage/common/pkgs/ioswitch"
  8. )
  9. type OnStreamBegin struct {
  10. Raw *ioswitch.StreamVar `json:"raw"`
  11. New *ioswitch.StreamVar `json:"new"`
  12. Signal *ioswitch.SignalVar `json:"signal"`
  13. }
  14. func (o *OnStreamBegin) Execute(ctx context.Context, sw *ioswitch.Switch) error {
  15. err := sw.BindVars(ctx, o.Raw)
  16. if err != nil {
  17. return err
  18. }
  19. o.New.Stream = o.Raw.Stream
  20. sw.PutVars(o.New, o.Signal)
  21. return nil
  22. }
  23. type OnStreamEnd struct {
  24. Raw *ioswitch.StreamVar `json:"raw"`
  25. New *ioswitch.StreamVar `json:"new"`
  26. Signal *ioswitch.SignalVar `json:"signal"`
  27. }
  28. type onStreamEnd struct {
  29. inner io.ReadCloser
  30. callback *future.SetVoidFuture
  31. }
  32. func (o *onStreamEnd) Read(p []byte) (n int, err error) {
  33. n, err = o.inner.Read(p)
  34. if err == io.EOF {
  35. o.callback.SetVoid()
  36. } else if err != nil {
  37. o.callback.SetError(err)
  38. }
  39. return n, err
  40. }
  41. func (o *onStreamEnd) Close() error {
  42. o.callback.SetError(fmt.Errorf("stream closed early"))
  43. return o.inner.Close()
  44. }
  45. func (o *OnStreamEnd) Execute(ctx context.Context, sw *ioswitch.Switch) error {
  46. err := sw.BindVars(ctx, o.Raw)
  47. if err != nil {
  48. return err
  49. }
  50. cb := future.NewSetVoid()
  51. o.New.Stream = &onStreamEnd{
  52. inner: o.Raw.Stream,
  53. callback: cb,
  54. }
  55. sw.PutVars(o.New)
  56. err = cb.Wait(ctx)
  57. if err != nil {
  58. return err
  59. }
  60. sw.PutVars(o.Signal)
  61. return nil
  62. }
  63. type HoldUntil struct {
  64. Waits []*ioswitch.SignalVar `json:"waits"`
  65. Holds []ioswitch.Var `json:"holds"`
  66. Emits []ioswitch.Var `json:"emits"`
  67. }
  68. func (w *HoldUntil) Execute(ctx context.Context, sw *ioswitch.Switch) error {
  69. err := sw.BindVars(ctx, w.Holds...)
  70. if err != nil {
  71. return err
  72. }
  73. err = ioswitch.BindArrayVars(sw, ctx, w.Waits)
  74. if err != nil {
  75. return err
  76. }
  77. for i := 0; i < len(w.Holds); i++ {
  78. err := ioswitch.AssignVar(w.Holds[i], w.Emits[i])
  79. if err != nil {
  80. return err
  81. }
  82. }
  83. sw.PutVars(w.Emits...)
  84. return nil
  85. }
  86. type HangUntil struct {
  87. Waits []*ioswitch.SignalVar `json:"waits"`
  88. Op ioswitch.Op `json:"op"`
  89. }
  90. func (h *HangUntil) Execute(ctx context.Context, sw *ioswitch.Switch) error {
  91. err := ioswitch.BindArrayVars(sw, ctx, h.Waits)
  92. if err != nil {
  93. return err
  94. }
  95. return h.Op.Execute(ctx, sw)
  96. }
  97. type Broadcast struct {
  98. Source *ioswitch.SignalVar `json:"source"`
  99. Targets []*ioswitch.SignalVar `json:"targets"`
  100. }
  101. func (b *Broadcast) Execute(ctx context.Context, sw *ioswitch.Switch) error {
  102. err := sw.BindVars(ctx, b.Source)
  103. if err != nil {
  104. return err
  105. }
  106. ioswitch.PutArrayVars(sw, b.Targets)
  107. return nil
  108. }
  109. func init() {
  110. OpUnion.AddT((*OnStreamBegin)(nil))
  111. OpUnion.AddT((*OnStreamEnd)(nil))
  112. OpUnion.AddT((*HoldUntil)(nil))
  113. OpUnion.AddT((*HangUntil)(nil))
  114. OpUnion.AddT((*Broadcast)(nil))
  115. }

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