support for private zrok-direct targets (#511)

This commit is contained in:
Michael Quigley 2024-01-09 14:26:07 -05:00
parent a95476bbe7
commit a28aa2f77f
No known key found for this signature in database
GPG Key ID: 9B60314A9DD20A62
3 changed files with 120 additions and 21 deletions

View File

@ -50,24 +50,33 @@ func (cmd *copyCommand) run(_ *cobra.Command, args []string) {
tui.Error("error loading root", err)
}
var access *sdk.Access
var srcAccess *sdk.Access
if sourceUrl.Scheme == "zrok" {
access, err = sdk.CreateAccess(root, &sdk.AccessRequest{ShareToken: sourceUrl.Host})
srcAccess, err = sdk.CreateAccess(root, &sdk.AccessRequest{ShareToken: sourceUrl.Host})
if err != nil {
tui.Error("error creating access", err)
}
}
if targetUrl.Scheme == "zrok" {
access, err = sdk.CreateAccess(root, &sdk.AccessRequest{ShareToken: targetUrl.Host})
if err != nil {
tui.Error("error creating access", err)
}
}
if access != nil {
if srcAccess != nil {
defer func() {
err := sdk.DeleteAccess(root, access)
err := sdk.DeleteAccess(root, srcAccess)
if err != nil {
tui.Error("error deleting access", err)
tui.Error("error deleting source access", err)
}
}()
}
var dstAccess *sdk.Access
if targetUrl.Scheme == "zrok" {
dstAccess, err = sdk.CreateAccess(root, &sdk.AccessRequest{ShareToken: targetUrl.Host})
if err != nil {
tui.Error("error creating access", err)
}
}
if dstAccess != nil {
defer func() {
err := sdk.DeleteAccess(root, dstAccess)
if err != nil {
tui.Error("error deleting target access", err)
}
}()
}
@ -93,11 +102,10 @@ func (cmd *copyCommand) createTarget(t *url.URL, root env_core.Root) (sync.Targe
case "file":
return sync.NewFilesystemTarget(&sync.FilesystemTargetConfig{Root: t.Path}), nil
case "zrok":
return sync.NewZrokTarget(&sync.ZrokTargetConfig{URL: t, Root: root})
default:
target, err := sync.NewWebDAVTarget(&sync.WebDAVTargetConfig{URL: t, Username: "", Password: "", Root: root})
if err != nil {
return nil, err
}
return target, nil
return sync.NewWebDAVTarget(&sync.WebDAVTargetConfig{URL: t, Username: "", Password: ""})
}
}

View File

@ -2,7 +2,6 @@ package sync
import (
"context"
"github.com/openziti/zrok/environment/env_core"
"github.com/openziti/zrok/util/sync/driveClient"
"io"
"net/http"
@ -15,13 +14,11 @@ type WebDAVTargetConfig struct {
URL *url.URL
Username string
Password string
Root env_core.Root
}
type WebDAVTarget struct {
cfg *WebDAVTargetConfig
dc *driveClient.Client
isDir bool
cfg *WebDAVTargetConfig
dc *driveClient.Client
}
func NewWebDAVTarget(cfg *WebDAVTargetConfig) (*WebDAVTarget, error) {

94
util/sync/zrok.go Normal file
View File

@ -0,0 +1,94 @@
package sync
import (
"context"
"github.com/openziti/zrok/environment/env_core"
"github.com/openziti/zrok/sdk/golang/sdk"
"github.com/openziti/zrok/util/sync/driveClient"
"io"
"net"
"net/http"
"net/url"
"os"
"path/filepath"
"strings"
"time"
)
type ZrokTargetConfig struct {
URL *url.URL
Username string
Password string
Root env_core.Root
}
type ZrokTarget struct {
cfg *ZrokTargetConfig
dc *driveClient.Client
}
type zrokDialContext struct {
root env_core.Root
}
func (zdc *zrokDialContext) Dial(_ context.Context, _, addr string) (net.Conn, error) {
share := strings.Split(addr, ":")[0]
return sdk.NewDialer(share, zdc.root)
}
func NewZrokTarget(cfg *ZrokTargetConfig) (*ZrokTarget, error) {
transport := http.DefaultTransport.(*http.Transport).Clone()
transport.DialContext = (&zrokDialContext{cfg.Root}).Dial
transport.TLSClientConfig.InsecureSkipVerify = true
httpUrl := strings.Replace(cfg.URL.String(), "zrok:", "http:", 1)
dc, err := driveClient.NewClient(&http.Client{Transport: transport}, httpUrl)
if err != nil {
return nil, err
}
return &ZrokTarget{cfg: cfg, dc: dc}, nil
}
func (t *ZrokTarget) Inventory() ([]*Object, error) {
fis, err := t.dc.Readdir(context.Background(), "", true)
if err != nil {
return nil, err
}
var objects []*Object
for _, fi := range fis {
if fi.Path != "/" {
objects = append(objects, &Object{
Path: fi.Path,
IsDir: fi.IsDir,
Size: fi.Size,
Modified: fi.ModTime,
ETag: fi.ETag,
})
}
}
return objects, nil
}
func (t *ZrokTarget) Mkdir(path string) error {
return t.dc.Mkdir(context.Background(), filepath.Join(t.cfg.URL.Path, path))
}
func (t *ZrokTarget) ReadStream(path string) (io.ReadCloser, error) {
return t.dc.Open(context.Background(), filepath.Join(t.cfg.URL.Path, path))
}
func (t *ZrokTarget) WriteStream(path string, rs io.Reader, _ os.FileMode) error {
ws, err := t.dc.Create(context.Background(), filepath.Join(t.cfg.URL.Path, path))
if err != nil {
return err
}
defer func() { _ = ws.Close() }()
_, err = io.Copy(ws, rs)
if err != nil {
return err
}
return nil
}
func (t *ZrokTarget) SetModificationTime(path string, mtime time.Time) error {
return t.dc.Touch(context.Background(), filepath.Join(t.cfg.URL.Path, path), mtime)
}