func Stream(w io.Writer, dir, relativePath string, writeFunc func(f os.FileInfo, shardRelativePath, fullPath string, tw *tar.Writer) error) error {
	tw := tar.NewWriter(w)
	defer tw.Close()
	if writeFunc == nil {
		writeFunc = StreamFile
	}
	return filepath.Walk(dir, func(path string, f os.FileInfo, err error) error {
		if err != nil {
			return err
		}
		if dir == path && f.IsDir() {
			return nil
		}
		subDir, _ := filepath.Split(path)
		subDir, err = filepath.Rel(dir, subDir)
		if err != nil {
			return err
		}
		return writeFunc(f, filepath.Join(relativePath, subDir), path, tw)
	})
}
Stream is a convenience function for creating a tar of a shard dir. It walks over the directory and subdirs,
possibly writing each file to a tar writer stream.  By default StreamFile is used, which will result in all files
being written.  A custom writeFunc can be passed so that each file may be written, modified+written, or skipped
depending on the custom logic.
package tar
import (
	"archive/tar"
	"fmt"
	"io"
	"os"
	"path/filepath"
	"strings"
	"time"
)