diff --git a/cmd/password.go b/cmd/password.go
new file mode 100644
index 0000000000000000000000000000000000000000..33e15c88941bd3dd2c809d8d838e5da0f94c7fc6
--- /dev/null
+++ b/cmd/password.go
@@ -0,0 +1,62 @@
+package cmd
+
+import (
+	"crypto/rand"
+	"encoding/base64"
+	"errors"
+	"fmt"
+
+	"github.com/spf13/cobra"
+	"gitlab.brickchain.com/tools/vaultenv/vault"
+)
+
+var passwordCmd = &cobra.Command{
+	Use:   "password [flags] path",
+	Short: "password Retrieve a password stored in vault.",
+	Long:  `password Retrieve a password stored in vault. Creates a new password if none exists`,
+	RunE: func(cmd *cobra.Command, args []string) error {
+
+		if len(args) < 1 {
+			return errors.New("Expected at least 1 argument")
+		}
+
+		data, err := vault.GetSecret(args[0])
+		if err != nil {
+			if vault_err, ok := err.(*vault.Error); ok {
+				if vault_err.Status != 404 {
+					return err
+				}
+
+				data, err = createPwd(args[0])
+				if err != nil {
+					return err
+				}
+			} else {
+				return err
+			}
+		}
+
+		fmt.Println(data["PASSWORD"].(string))
+
+		return nil
+
+	},
+}
+
+func createPwd(path string) (map[string]interface{}, error) {
+
+	// generate random string of 32 bytes
+	b := make([]byte, 32)
+	if _, err := rand.Read(b); err != nil {
+		return nil, err
+	}
+
+	data := make(map[string]interface{})
+	data["PASSWORD"] = base64.URLEncoding.EncodeToString(b)
+
+	return data, vault.PostSecret(path, data)
+}
+
+func init() {
+	RootCmd.AddCommand(passwordCmd)
+}
diff --git a/cmd/read.go b/cmd/read.go
index a652661ae46074f4b40009c1fae55227d7ebb610..654b3771999532b7d422a525fb2cc90dbd5576fa 100644
--- a/cmd/read.go
+++ b/cmd/read.go
@@ -16,22 +16,39 @@ import (
 
 var shellFormat bool
 
+// eval $(vaultenv read -s ...)
+// vaultenv.exe read -s powershell ... | Invoke-Expression
+// vaultenv.exe read -s cmd ..., then copy and paste into shell
 var readCmd = &cobra.Command{
 	Use:   "read [flags] path",
 	Short: "read Short",
 	Long:  `read Long`,
 	RunE: func(cmd *cobra.Command, args []string) (err error) {
-		if len(args) != 1 {
+		if len(args) < 1 {
 			return errors.New("Expected 1 argument")
 		}
-		data, err := vault.GetSecret(args[0])
+		data, err := vault.GetSecret(args[len(args)-1])
 		if data != nil {
 			if shellFormat {
+				shell := "default"
+				if len(args) > 1 {
+					shell = args[0]
+				}
 				for k, v := range data {
 					qv := strconv.QuoteToASCII(v.(string))
-					qv = strings.Replace(qv, "'", "\\x27", -1)
-					qv = qv[1 : len(qv)-1]
-					fmt.Printf("%s=$'%s'; export %s;\n", k, qv, k)
+					switch shell {
+					case "ps":
+						fmt.Printf("$Env:%s = %s\n", k, qv)
+					case "powershell":
+						fmt.Printf("$Env:%s = %s\n", k, qv)
+					case "cmd":
+						qv = qv[1 : len(qv)-1]
+						fmt.Printf("set %s=%s\n", k, qv)
+					default:
+						qv = strings.Replace(qv, "'", "\\x27", -1)
+						qv = qv[1 : len(qv)-1]
+						fmt.Printf("%s=$'%s'; export %s;\n", k, qv, k)
+					}
 				}
 			} else {
 				b, _ := json.MarshalIndent(data, "", "\t")
diff --git a/cmd/upload.go b/cmd/upload.go
new file mode 100644
index 0000000000000000000000000000000000000000..92dc406082bd64a2a4e681ba8d653bacb74bedc5
--- /dev/null
+++ b/cmd/upload.go
@@ -0,0 +1,32 @@
+package cmd
+
+import (
+	"encoding/base64"
+	"errors"
+	"io/ioutil"
+
+	"github.com/spf13/cobra"
+	"gitlab.hedenstroem.com/go/vaultenv/vault"
+)
+
+var uploadCmd = &cobra.Command{
+	Use:   "upload [flags] path file",
+	Short: "upload Short",
+	Long:  `upload Long`,
+	RunE: func(cmd *cobra.Command, args []string) (err error) {
+		if len(args) != 2 {
+			return errors.New("Expected 2 arguments; path and file.")
+		}
+		b, err := ioutil.ReadFile(args[1])
+		if b != nil {
+			data := make(map[string]interface{})
+			data["file"] = base64.StdEncoding.EncodeToString(b)
+			err = vault.PostSecret(args[0], data)
+		}
+		return
+	},
+}
+
+func init() {
+	RootCmd.AddCommand(uploadCmd)
+}