diff --git a/README.md b/README.md index a9ee2ed..ac39b7f 100644 --- a/README.md +++ b/README.md @@ -16,6 +16,7 @@ development. [RFC 1939](https://www.ietf.org/rfc/rfc1939.txt) document has been * NOOP * RSET * QUIT +* TOP ### Installation @@ -79,6 +80,10 @@ func main() { // LIST command ll, _ := pop.List(1) fmt.Println(ll[0]) + + // TOP msgNum n + top, _ := pop.Top(1, 10) + fmt.Println(top) // DELE command dele, err := pop.Dele("1") diff --git a/example/main.go b/example/main.go index 5bd3ae0..34881de 100644 --- a/example/main.go +++ b/example/main.go @@ -44,6 +44,9 @@ func main() { list, _ = pop.List(1) // LIST command fmt.Println(list) // 1st message size + top, _ := pop.Top(1, 10) // TOP msgNum n + fmt.Println(top) // Headers, blank line, and top 10 line of the message body in an array + n, _ := pop.Noop() // NOOP command fmt.Println(n) // +OK diff --git a/pop3/transaction.go b/pop3/transaction.go index f95759b..d10c66d 100644 --- a/pop3/transaction.go +++ b/pop3/transaction.go @@ -397,10 +397,31 @@ func (c *Client) pass(password string) (string, error) { return passResp, nil } +// Top is a command which fetches message (msgNum) with n lines. To get messages +// from mail server, you need to authenticate. The response starts with "+OK" +// status indicator, and it follows the multiline mail. The server sends header +// of the message, the blank line separating the headers from the body, and then +// the number of lines of the message's body. If you request the message line +// number greater than the number of lines in the body, the mail server sends +// the entire message. +// Possible responses: +// +OK message follows +// -ERR no such message +// Example: +// C: TOP 1 10 +// S: +OK message follows +// S: +// S: . +// ... +// C: TOP 100 10 +// S: -ERR no such message +// +// msgNum indicates message id starts from 1 and n is line of the message's body. func (c *Client) Top(msgNum, n int) ([]string, error) { return c.top(msgNum, n) } +// top is the implementation function of the Top function. func (c *Client) top(msgNum, n int) ([]string, error) { if msgNum < 1 { return nil, fmt.Errorf("%s message number should be greater than 0", e) diff --git a/pop3/transaction_test.go b/pop3/transaction_test.go index ab98fbc..3196198 100644 --- a/pop3/transaction_test.go +++ b/pop3/transaction_test.go @@ -549,3 +549,63 @@ func TestTopNegativeN(t *testing.T) { } log.Println("Connection closed") } + +func TestTopNotLoggedIn(t *testing.T) { + pop, err := Connect(gmailTLSAddr, nil, true) + if err != nil { + t.Errorf(err.Error()) + } + log.Println("Connection established") + + top, err := pop.Top(1, 20) + if err != nil { + t.Errorf("err need to be ") + } + if !strings.HasPrefix(top[0], e) { + t.Errorf(top[0]) + } + log.Println(top[0]) + log.Println(err) +} + +func TestTopPass(t *testing.T) { + pop, err := Connect(gmailTLSAddr, nil, true) + if err != nil { + t.Errorf(err.Error()) + } + log.Println("Connection established") + + username := os.Getenv(userKey) + u, err := pop.User(username) + if err != nil { + t.Errorf(err.Error()) + } + if !strings.HasPrefix(u, ok) { + t.Errorf("expected: %s, got: %s", ok, u) + } + + password := os.Getenv(passwordKey) + p, err := pop.Pass(password) + if err != nil { + t.Errorf(err.Error()) + } + if !strings.HasPrefix(p, ok) { + t.Errorf("expected: %s, got: %s", ok, p) + } + + top, err := pop.Top(1, 20) + if err != nil { + t.Errorf(err.Error()) + } + if !strings.HasPrefix(top[0], ok) { + t.Errorf(top[0]) + } + log.Println(top[0]) + + quit, err := pop.Quit() + if err != nil { + t.Errorf(err.Error()) + } + log.Println(quit) + log.Println("Connection closed") +}