Commit 8ea4f474457a0591b9b130e45c8fcf161bdf035e

Parents: 27d49fd8496c045f9c176d63b0efc40d3394adcf

From: Moritz Poldrack <git@moritz.sh>
Date: Fri Jun 10 22:53:09 2022 +0700

added HELP command

		

Stats

README.md +1/-1
mandatory.go +14/-0
mandatory_test.go +39/-0
status.go +1/-0

Changeset

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
diff --git a/README.md b/README.md
index e0a6f58d05ad45bf73e94816d588defe449e3a93..a06939182cbbf6b0d32724aef3336b6c77c1a3e3 100644
--- a/README.md
+++ b/README.md
@@ -10,7 +10,7 @@ | Command           | Capability    | Implemented | Standard |
 |-------------------|---------------|-------------|----------|
 | CAPABILITIES      | mandatory     | 🗸           | RFC3977  |
 | HEAD              | mandatory     | 🗸           | RFC3977  |
-| HELP              | mandatory     | ☓           | RFC3977  |
+| HELP              | mandatory     | 🗸           | RFC3977  |
 | QUIT              | mandatory     | ☓           | RFC3977  |
 | STAT              | mandatory     | ☓           | RFC3977  |
 | AUTHINFO USER     | AUTHINFO USER | 🗸           | RFC4643  |
diff --git a/mandatory.go b/mandatory.go
index 399b18a24b8100693c7c37913a8f7aacc3fd7abd..b0c685f17263675b899093f4f3e3b5c488438e9c 100644
--- a/mandatory.go
+++ b/mandatory.go
@@ -39,3 +39,17 @@ 	default:
 		return nil, ErrUnexpectedResponse
 	}
 }
+
+func (c *Conn) Help(ctx context.Context) (string, error) {
+	resp, err := c.Cmd(ctx, "HELP")
+	if err != nil {
+		return "", fmt.Errorf("failed to get helptext: %w", err)
+	}
+
+	switch resp.Status.Code {
+	case StatusHelpTextFollows:
+		return fmt.Sprintf("%s", resp.Body), nil
+	default:
+		return "", ErrUnexpectedResponse
+	}
+}
diff --git a/mandatory_test.go b/mandatory_test.go
index 323f73ebb377a264b383680b87470432e2199acd..d97fe725e12639a4d88354443eca4e89e6fac8b8 100644
--- a/mandatory_test.go
+++ b/mandatory_test.go
@@ -3,6 +3,7 @@
 import (
 	"context"
 	"errors"
+	"strings"
 	"testing"
 	"time"
 
@@ -113,3 +114,41 @@ 			}
 		})
 	}
 }
+
+func TestHelp(t *testing.T) {
+	c, err := nntp.Dial(NewsServerPlain, nntp.OptionUnencrypted)
+	if err != nil {
+		t.Skipf("connection to '%s' failed: %v", NewsServerSecure, err)
+	}
+
+	ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second)
+	defer cancel()
+	err = c.LoginUserPass(ctx, NewsServerUser, NewsServerPassword)
+	if err != nil {
+		t.Skipf("failed to authenticate: %v", err)
+	}
+
+	ctx, cancel = context.WithTimeout(context.Background(), 5*time.Second)
+	defer cancel()
+	help, err := c.Help(ctx)
+	if err != nil {
+		t.Errorf("requesting help failed: %v", err)
+	}
+
+	contained := make(map[string]bool)
+	for _, v := range strings.Split(help, "\n") {
+		v = strings.TrimLeft(v, "  ")
+		contained[strings.Split(v, " ")[0]] = true
+	}
+
+	mandatory := []string{
+		"quit",
+		"head",
+		"stat",
+	}
+	for _, key := range mandatory {
+		if !contained[key] {
+			t.Errorf("mandatory command '%s' is missing", key)
+		}
+	}
+}
diff --git a/status.go b/status.go
index 5d6880a5fb8eefa37e51b6cc2ad26d3917807691..b62a344a58fac463e2109568f4b5530792dba5f3 100644
--- a/status.go
+++ b/status.go
@@ -3,6 +3,7 @@
 import "errors"
 
 const (
+	StatusHelpTextFollows             = 100
 	StatusServiceAvailable            = 200
 	StatusServiceNoPosting            = 201
 	StatusGroupSelected               = 211