diff --git a/NOTES.md b/NOTES.md
index 46182bb7a426f075ca98b93fb46eb6efe662dfff..94e264d84a993f80d9d9bda6cb9b0c7e224ddf7a 100644
--- a/NOTES.md
+++ b/NOTES.md
@@ -29,15 +29,15 @@ repl.commands?
 
   * Run [godoc](http://localhost:6060/) and then review where the help text is lacking.
   * ~~Move to a storage layer.~~
-  * this.Folder should be a storage.Folder.
   * Implement each command.
     * Next: folder commands - ~~CREATE~~, ~~REMOVE~~, MODIFY, ~~INDEX~~, ~~SELECT~~
     * Messages: ~~ADD~~, ~~CURRENT~~, ~~DIRECTORY~~, ~~BACK~~, CHANGE,
-                ~~FIRST~~, ~~NEXT~~, ~~READ~~, DELETE
+                ~~FIRST~~, ~~NEXT~~, ~~READ~~, ~~DELETE~~
     * Messages edit: CHANGE, REPLY, FORWARD
     * Moving messages: COPY, MOVE
     * Compound commands: SET and SHOW - make HELP work for them.
     * Mail: MAIL, FORWARD, 
+  * Run this.Skew.Safe() before... each command?  each write?
   * Handle broadcast messages - have bulletin watch a directory and
     display files from it.  Then have them delete the file if it's older
     than 5 minutes (allow for failure)
@@ -71,7 +71,8 @@ Done:
      * ~~expire~~
   * ~~Add a pager~~
   * ~~SHOW VERSION~~
-  * Check db version; notify user if it changes; refuse to write to db if it has.
+  * ~~Check db version; notify user if it changes; refuse to write to db if it has.~~
+  * ~~this.Folder should be a storage.Folder.~~
 
 ## Module links
 
diff --git a/folders/folders.go b/folders/folders.go
index d34bfefc2f8297be0f3af6c710fe258c06577f38..7f2245ceeddda13656ef8e1a05bb9532120e4d37 100644
--- a/folders/folders.go
+++ b/folders/folders.go
@@ -10,19 +10,19 @@ import (
 )
 
 // ValidFolder validates the folder name for this user.
-func ValidFolder(folder string) (string, error) {
+func ValidFolder(folder string) (storage.Folder, error) {
 	if strings.Contains(folder, "%") {
-		return "", errors.New("Folder name cannot contain a %")
+		return storage.Folder{}, errors.New("Folder name cannot contain a %")
 	}
 	correct := FindFolder(folder)
-	if correct == "" {
-		return "", errors.New("Unable to select the folder")
+	if correct.Name == "" {
+		return storage.Folder{}, errors.New("Unable to select the folder")
 	}
-	if !IsFolderAccess(correct, this.User.Login) {
+	if !IsFolderAccess(correct.Name, this.User.Login) {
 		// TODO: Should be:
 		//       WRITE(6,'('' You are not allowed to access folder.'')')
 		//       WRITE(6,'('' See '',A,'' if you wish to access folder.'')')
-		return "", errors.New("Unable to select the folder")
+		return storage.Folder{}, errors.New("Unable to select the folder")
 	}
 	return correct, nil
 }
@@ -77,10 +77,10 @@ func ListFolder() ([]storage.ListFolderRow, error) {
 }
 
 // FindFolder finds a folder based on the prefix.
-func FindFolder(name string) string {
+func FindFolder(name string) storage.Folder {
 	ctx := storage.Context()
 	folder, _ := this.Q.FindFolderExact(ctx, name)
-	if folder != "" {
+	if folder.Name != "" {
 		return folder
 	}
 	folder, _ = this.Q.FindFolderPrefix(ctx, name)
diff --git a/folders/messages.go b/folders/messages.go
index 6eeb8eb16203f99b8b86aeca779411122aeec7b8..d05b8e4e78b125038be7fea19698186fdaebb6ec 100644
--- a/folders/messages.go
+++ b/folders/messages.go
@@ -67,7 +67,7 @@ func MarkSeen(msgids []int64) error {
 	for _, msgid := range msgids {
 		this.Q.SetMessageSeen(ctx, storage.SetMessageSeenParams{
 			Login:  this.User.Login,
-			Folder: this.Folder,
+			Folder: this.Folder.Name,
 			Msgid:  msgid,
 		})
 	}
@@ -81,7 +81,7 @@ func MarkUnseen(msgids []int64) error {
 	for _, msgid := range msgids {
 		this.Q.UnsetMessageSeen(ctx, storage.UnsetMessageSeenParams{
 			Login:  this.User.Login,
-			Folder: this.Folder,
+			Folder: this.Folder.Name,
 			Msgid:  msgid,
 		})
 	}
@@ -137,3 +137,24 @@ func ListMessages(folder string) ([]storage.Message, error) {
 	rows, err := this.Q.ListMessages(ctx, folder)
 	return rows, err
 }
+
+// DeleteMessages deletes a list of messages.
+func DeleteMessages(msgids []int64) error {
+	ctx := storage.Context()
+
+	for _, msgid := range msgids {
+		this.Q.DeleteMessage(ctx, storage.DeleteMessageParams{
+			Folder: this.Folder.Name,
+			ID:     msgid,
+		})
+	}
+	return nil
+}
+
+// DeleteAllMessages deletes all messages in a folder.
+func DeleteAllMessages() error {
+	ctx := storage.Context()
+
+	this.Q.DeleteAllMessages(ctx, this.Folder.Name)
+	return nil
+}
diff --git a/repl/command.go b/repl/command.go
index 83167dfd28d992e161d53081db3df8027c01ce21..8b63bd69d5462ffebdf622a5a9ff7a91e4b715e1 100644
--- a/repl/command.go
+++ b/repl/command.go
@@ -396,8 +396,7 @@ of the message again, you can enter the CURRENT command.
 message is  deleted. Only the  original owner  or a privileged  user can
 delete a message. Note that the  message is not deleted immediately, but
 its expiration is set 15 minutes in  the future. This is to allow a user
-to  recover the  message using  the UNDELETE  command. If  you want  the
-message deleted immediately, use the /IMMEDIATE qualifier.
+to  recover the  message using  the UNDELETE  command.
 
   Format:
     DELETE [message_number][-message_number1]
@@ -410,26 +409,13 @@ specified if the folder is remote.
 The key words  CURRENT and LAST can  also be specified in  the range in,
 place of an actual number, i.e. CURRENT-LAST, 1-CURRENT, etc.`,
 		MaxArgs: 1,
+		Action:  ActionDelete,
 		Flags: dclish.Flags{
 			"/ALL": {
 				Description: `  Specifies to delete all the messages in the folder.  Note:  This will
   not work for remote folders.  Only one message can be deleted from a
   remote folder at a time.`,
 			},
-			"/IMMEDIATE": {
-				Description: `  Specifies that the message is to be deleted immediately.`,
-			},
-			"/SUBJECT": {
-				Description: `/SUBJECT=subject
-
-  Specifies the subject of the bulletin to be deleted at a remote DECNET
-  node. The DECNET node must be  specified with the /NODE qualifier. The
-  specified subject need not be the exact subject of the message. It can
-  be a substring of the subject. This  is in case you have forgotten the
-  exact subject  that was  specified. Case is  not critical  either. You
-  will be notified if the deletion was successful.`,
-				OptArg: true,
-			},
 		},
 	},
 	"DIRECTORY": {
diff --git a/repl/folders.go b/repl/folders.go
index da4b0a925c0e7249dd0df912b4b1aafa58166ee4..8c4b29d014ed53cf2852cff030dd0f897eb979fc 100644
--- a/repl/folders.go
+++ b/repl/folders.go
@@ -101,12 +101,12 @@ func ActionSelect(cmd *dclish.Command) error {
 		return errors.New("Folder name cannot contain a %")
 	}
 	folder := folders.FindFolder(cmd.Args[0])
-	if folder == "" {
+	if folder.Name == "" {
 		return errors.New("Unable to select the folder")
 	}
-	if folders.IsFolderAccess(folder, this.User.Login) {
+	if folders.IsFolderAccess(folder.Name, this.User.Login) {
 		this.Folder = folder
-		fmt.Printf("Folder has been set to '%s'.\n", folder)
+		fmt.Printf("Folder has been set to '%s'.\n", folder.Name)
 		return nil
 	}
 	// TODO: Should be:
diff --git a/repl/messages.go b/repl/messages.go
index 9e5f223be6e9f6a89b5c55ac865503129bb8deeb..3368838f1ddd7c88e076d3a0fb542c84143d80e1 100644
--- a/repl/messages.go
+++ b/repl/messages.go
@@ -31,7 +31,7 @@ func ActionDirectory(cmd *dclish.Command) error {
 		}
 		this.Folder = folder
 	}
-	msgs, err := folders.ListMessages(this.Folder)
+	msgs, err := folders.ListMessages(this.Folder.Name)
 	if err != nil {
 		return err
 	}
@@ -125,7 +125,7 @@ func ActionAdd(cmd *dclish.Command) error {
 	fmt.Printf("TODO: optSystem is not yet implemented - you set it to %d\n", optSystem)
 
 	if len(optFolder) == 0 {
-		optFolder = []string{this.Folder}
+		optFolder = []string{this.Folder.Name}
 	}
 	// TODO: check if folders exist.
 	if optSubject == "" {
@@ -150,7 +150,7 @@ func ActionAdd(cmd *dclish.Command) error {
 // ActionCurrent handles the `CURRENT` command.
 func ActionCurrent(_ *dclish.Command) error {
 	// TODO: handle flags.
-	msg, err := folders.ReadMessage(this.User.Login, this.Folder, this.MsgID)
+	msg, err := folders.ReadMessage(this.User.Login, this.Folder.Name, this.MsgID)
 	if err != nil {
 		return err
 	}
@@ -165,12 +165,12 @@ func ActionCurrent(_ *dclish.Command) error {
 // ActionBack handles the `BACK` command.
 func ActionBack(_ *dclish.Command) error {
 	// TODO: handle flags.
-	msgid := folders.PrevMsgid(this.User.Login, this.Folder, this.MsgID)
+	msgid := folders.PrevMsgid(this.User.Login, this.Folder.Name, this.MsgID)
 	if msgid == 0 {
 		fmt.Println("No previous messages")
 		return nil
 	}
-	msg, err := folders.ReadMessage(this.User.Login, this.Folder, msgid)
+	msg, err := folders.ReadMessage(this.User.Login, this.Folder.Name, msgid)
 	if err != nil {
 		return err
 	}
@@ -189,7 +189,7 @@ func ActionChange(cmd *dclish.Command) error {
 
 // ActionFirst handles the `FIRST` command.
 func ActionFirst(_ *dclish.Command) error {
-	msgid := folders.FirstMessage(this.Folder)
+	msgid := folders.FirstMessage(this.Folder.Name)
 	if msgid == 0 {
 		fmt.Println("No messages in folder")
 		return nil
@@ -201,12 +201,12 @@ func ActionFirst(_ *dclish.Command) error {
 // ActionNext handles the `NEXT` command.
 func ActionNext(_ *dclish.Command) error {
 	// TODO: handle flags.
-	msgid := folders.NextMsgid(this.User.Login, this.Folder, this.MsgID)
+	msgid := folders.NextMsgid(this.User.Login, this.Folder.Name, this.MsgID)
 	if msgid == 0 {
 		fmt.Println("No next messages")
 		return nil
 	}
-	msg, err := folders.ReadMessage(this.User.Login, this.Folder, msgid)
+	msg, err := folders.ReadMessage(this.User.Login, this.Folder.Name, msgid)
 	if err != nil {
 		return err
 	}
@@ -228,14 +228,14 @@ func ActionRead(cmd *dclish.Command) error {
 			return err
 		}
 	}
-	msg, err := folders.ReadMessage(this.User.Login, this.Folder, msgid)
+	msg, err := folders.ReadMessage(this.User.Login, this.Folder.Name, msgid)
 	if err != nil {
 		return err
 	}
 	// TODO: pager needs to report if the whole message was read
 	// and only increment if not.
 	pager.Pager(msg.String())
-	msgid = folders.NextMsgid(this.User.Login, this.Folder, msgid)
+	msgid = folders.NextMsgid(this.User.Login, this.Folder.Name, msgid)
 	this.MsgID = max(this.MsgID, msgid)
 	return nil
 }
@@ -285,3 +285,39 @@ func ActionUnseen(cmd *dclish.Command) error {
 	}
 	return nil
 }
+
+// ActionDelete handles the `DELETE` command.
+func ActionDelete(cmd *dclish.Command) error {
+	// TODO: Follow permissions.
+	var err error
+
+	all := false
+	if cmd.Flags["/ALL"].Value == "true" {
+		all = true
+	}
+	if all {
+		if len(cmd.Args) == 1 {
+			fmt.Println("ERROR: Can't specify both message numbers and /ALL flag.")
+			return nil
+		}
+		err := folders.DeleteAllMessages()
+		if err != nil {
+			fmt.Printf("ERROR: %s.\n", err)
+		}
+		return nil
+	}
+
+	msgids := []int64{this.MsgID}
+	if len(cmd.Args) == 1 {
+		msgids, err = ParseNumberList(cmd.Args[0])
+		if err != nil {
+			fmt.Printf("ERROR: %s.\n", err)
+			return nil
+		}
+	}
+	err = folders.DeleteMessages(msgids)
+	if err != nil {
+		fmt.Printf("ERROR: %s.\n", err)
+	}
+	return nil
+}
diff --git a/repl/set.go b/repl/set.go
index bd399cb3d919c4ec6ae9a2f79b0339b12a9f6b98..b72e0b30c26fe497fdbc5fb06fbe6f00ff75dcab 100644
--- a/repl/set.go
+++ b/repl/set.go
@@ -63,12 +63,12 @@ func ActionSetFolder(cmd *dclish.Command) error {
 		return errors.New("Folder name cannot contain a %")
 	}
 	folder := folders.FindFolder(cmd.Args[0])
-	if folder == "" {
+	if folder.Name == "" {
 		return errors.New("Unable to select the folder")
 	}
-	if folders.IsFolderAccess(folder, this.User.Login) {
+	if folders.IsFolderAccess(folder.Name, this.User.Login) {
 		this.Folder = folder
-		fmt.Printf("Folder has been set to '%s'.\n", folder)
+		fmt.Printf("Folder has been set to '%s'.\n", folder.Name)
 		return nil
 	}
 	// TODO: Should be:
diff --git a/storage/folders.sql.go b/storage/folders.sql.go
index 7b5bc42eaf4e208236a7760e86a1c4b22d077e60..4666356abaa920dd5acd07f222d8d98e7c2952ba 100644
--- a/storage/folders.sql.go
+++ b/storage/folders.sql.go
@@ -62,25 +62,53 @@ func (q *Queries) CreateFolder(ctx context.Context, arg CreateFolderParams) erro
 }
 
 const findFolderExact = `-- name: FindFolderExact :one
-SELECT name FROM folders where name = ?
+SELECT name, "always", brief, description, notify, readnew, shownew, system, expire, visibility, create_at, update_at FROM folders where name = ?
 `
 
-func (q *Queries) FindFolderExact(ctx context.Context, name string) (string, error) {
+func (q *Queries) FindFolderExact(ctx context.Context, name string) (Folder, error) {
 	row := q.db.QueryRowContext(ctx, findFolderExact, name)
-	err := row.Scan(&name)
-	return name, err
+	var i Folder
+	err := row.Scan(
+		&i.Name,
+		&i.Always,
+		&i.Brief,
+		&i.Description,
+		&i.Notify,
+		&i.Readnew,
+		&i.Shownew,
+		&i.System,
+		&i.Expire,
+		&i.Visibility,
+		&i.CreateAt,
+		&i.UpdateAt,
+	)
+	return i, err
 }
 
 const findFolderPrefix = `-- name: FindFolderPrefix :one
-SELECT name FROM folders where name LIKE ?
+SELECT name, "always", brief, description, notify, readnew, shownew, system, expire, visibility, create_at, update_at FROM folders where name LIKE ?
 ORDER BY name
 LIMIT 1
 `
 
-func (q *Queries) FindFolderPrefix(ctx context.Context, name string) (string, error) {
+func (q *Queries) FindFolderPrefix(ctx context.Context, name string) (Folder, error) {
 	row := q.db.QueryRowContext(ctx, findFolderPrefix, name)
-	err := row.Scan(&name)
-	return name, err
+	var i Folder
+	err := row.Scan(
+		&i.Name,
+		&i.Always,
+		&i.Brief,
+		&i.Description,
+		&i.Notify,
+		&i.Readnew,
+		&i.Shownew,
+		&i.System,
+		&i.Expire,
+		&i.Visibility,
+		&i.CreateAt,
+		&i.UpdateAt,
+	)
+	return i, err
 }
 
 const getFolderExpire = `-- name: GetFolderExpire :one
diff --git a/storage/messages.sql.go b/storage/messages.sql.go
index ac9ea85e3778ffb187304e15b0c4ec0c984730ac..9f51c306905db459aa4606b08bdf1cf2121aff58 100644
--- a/storage/messages.sql.go
+++ b/storage/messages.sql.go
@@ -41,6 +41,15 @@ func (q *Queries) CreateMessage(ctx context.Context, arg CreateMessageParams) er
 	return err
 }
 
+const deleteAllMessages = `-- name: DeleteAllMessages :exec
+DELETE FROM messages WHERE folder = ?
+`
+
+func (q *Queries) DeleteAllMessages(ctx context.Context, folder string) error {
+	_, err := q.db.ExecContext(ctx, deleteAllMessages, folder)
+	return err
+}
+
 const nextMsgid = `-- name: NextMsgid :one
 SELECT CAST(COALESCE(MIN(id), 0) AS INT) FROM messages AS m
   WHERE m.folder = ?1 AND m.id > ?2
diff --git a/storage/queries/folders.sql b/storage/queries/folders.sql
index 16183321535b352140fc38df3963d1a9abecab54..da30c3f92c19c57c05d9420d7c9daf9f821196f9 100644
--- a/storage/queries/folders.sql
+++ b/storage/queries/folders.sql
@@ -22,10 +22,10 @@ GROUP By f.name
 ORDER BY f.name;
 
 -- name: FindFolderExact :one
-SELECT name FROM folders where name = ?;
+SELECT * FROM folders where name = ?;
 
 -- name: FindFolderPrefix :one
-SELECT name FROM folders where name LIKE ?
+SELECT * FROM folders where name LIKE ?
 ORDER BY name
 LIMIT 1;
 
diff --git a/storage/queries/messages.sql b/storage/queries/messages.sql
index 52eed05f97927196f0da8bba8fd09ca9bbf6c999..7750b8fab03e6357f58c975307444aaa3960dea8 100644
--- a/storage/queries/messages.sql
+++ b/storage/queries/messages.sql
@@ -31,3 +31,6 @@ SELECT CAST(COALESCE(MAX(id), 0) AS INT) FROM messages AS m
 -- name: PrevMsgidIgnoringSeen :one
 SELECT CAST(MAX(id) AS INT) FROM messages AS m
   WHERE m.folder = ?1 AND m.id < ?2;
+
+-- name: DeleteAllMessages :exec
+DELETE FROM messages WHERE folder = ?;
diff --git a/this/this.go b/this/this.go
index c644852865b2d057d045fe6fba902c298b39e291..22a64268c981af8fa0e67e84b1ed8f912d2fa1e6 100644
--- a/this/this.go
+++ b/this/this.go
@@ -29,7 +29,7 @@ var Store *sqlx.DB
 var Q *storage.Queries
 
 // Folder is the current folder.
-var Folder string
+var Folder storage.Folder
 
 // MsgID is the current message id.
 var MsgID int64
@@ -73,19 +73,22 @@ func StartThis(login, name string) error {
 	if User.Disabled == 1 {
 		return errors.New("User is disabled")
 	}
-	Folder = "GENERAL"
+	Folder, err = Q.GetFolder(ctx, "GENERAL")
+	if err != nil {
+		return err
+	}
 	MsgID, err = Q.NextMsgid(ctx, storage.NextMsgidParams{
-		Folder: Folder,
+		Folder: Folder.Name,
 		ID:     0,
 		Login:  User.Login,
 	})
 	if MsgID == 0 {
 		MsgID, err = Q.NextMsgidIgnoringSeen(ctx, storage.NextMsgidIgnoringSeenParams{
-			Folder: Folder,
+			Folder: Folder.Name,
 			ID:     0,
 		})
 	}
 
-	fmt.Printf("User: %s\nFolder: %s\nMsgID: %d\n", User, Folder, MsgID)
+	fmt.Printf("User: %s\nFolder: %s\nMsgID: %d\n", User, Folder.Name, MsgID)
 	return nil
 }