Пример #1
0
// newIMAPClient will initiate a new IMAP connection with the given creds.
func newIMAPClient(info MailboxInfo) (*imap.Client, error) {
	var client *imap.Client
	var err error
	if info.TLS {
		client, err = imap.DialTLS(info.Host, new(tls.Config))
		if err != nil {
			return client, err
		}
	} else {
		client, err = imap.Dial(info.Host)
		if err != nil {
			return client, err
		}
	}

	_, err = client.Login(info.User, info.Pwd)
	if err != nil {
		return client, err
	}

	_, err = imap.Wait(client.Select(info.Folder, info.ReadOnly))
	if err != nil {
		return client, err
	}

	return client, nil
}
Пример #2
0
func dialImap(addr string) (c *imap.Client, err error) {
	if strings.HasSuffix(addr, ":993") {
		c, err = imap.DialTLS(addr, tlsConfig)
	} else {
		c, err = imap.Dial(addr)
	}
	if err != nil {
		return nil, e.New(err)
	}
	return c, nil
}
Пример #3
0
func Dial(addr string) (c *imap.Client) {
	var err error
	if strings.HasSuffix(addr, ":993") {
		c, err = imap.DialTLS(addr, nil)
	} else {
		c, err = imap.Dial(addr)
	}
	if err != nil {
		panic(err)
	}
	return c
}
Пример #4
0
func Dial(addr string) (c *imap.Client) {
	var err error
	if strings.HasSuffix(addr, ":993") {
		log.Println("Dialing with tls: ", addr)
		c, err = imap.DialTLS(addr, nil)
	} else {
		log.Println("Dialing without tls: ", addr)
		c, err = imap.Dial(addr)
	}
	if err != nil {
		panic(err)
	}
	return c
}
Пример #5
0
// CheckImapConnection if is connected return nil or try to connect
func (m *MatterMail) CheckImapConnection() error {
	if m.imapClient != nil && (m.imapClient.State() == imap.Auth || m.imapClient.State() == imap.Selected) {
		m.debg.Println("CheckImapConnection: Connection alive")
		return nil
	}

	var err error

	//Start connection with server
	if strings.HasSuffix(m.cfg.ImapServer, ":993") {
		m.debg.Println("CheckImapConnection: DialTLS")
		m.imapClient, err = imap.DialTLS(m.cfg.ImapServer, nil)
	} else {
		m.debg.Println("CheckImapConnection: Dial")
		m.imapClient, err = imap.Dial(m.cfg.ImapServer)
	}

	if err != nil {
		m.eror.Println("Unable to connect:", err)
		return err
	}

	if m.cfg.StartTLS && m.imapClient.Caps["STARTTLS"] {
		m.debg.Println("CheckImapConnection:StartTLS")
		var tconfig tls.Config
		if m.cfg.TLSAcceptAllCerts {
			tconfig.InsecureSkipVerify = true
		}
		_, err = m.imapClient.StartTLS(&tconfig)
		if err != nil {
			return err
		}
	}

	//Check if server support IDLE mode
	/*
		if !m.imapClient.Caps["IDLE"] {
			return fmt.Errorf("The server %q does not support IDLE\n", m.cfg.ImapServer)
		}
	*/
	m.info.Printf("Connected with %q\n", m.cfg.ImapServer)

	_, err = m.imapClient.Login(m.cfg.Email, m.cfg.EmailPass)
	if err != nil {
		m.eror.Println("Unable to login:", m.cfg.Email)
		return err
	}

	return nil
}
Пример #6
0
// dial open imap socket
func dial(host string) (*imap.Client, error) {
	var client *imap.Client
	var err error

	if strings.HasSuffix(host, ":993") {
		client, err = imap.DialTLS(host, nil)
	} else {
		client, err = imap.Dial(host)
	}

	if err != nil {
		return nil, err
	}

	return client, nil
}
Пример #7
0
func (mc *MailCon) dial() (c *imap.Client, err error) {
	// Decide what method to use for dialing into the server
	var serverAddr string = fmt.Sprintf("%s:%d", mc.conf.Hostname, mc.conf.Port)
	if 993 == mc.conf.Port {
		c, err = imap.DialTLS(serverAddr, nil)
	} else {
		c, err = imap.Dial(serverAddr)
	}
	// If dialing went wrong, return the error
	if err != nil {
		return nil, err
	}
	// Check for STARTTLS and use appropriate method and config object if need be
	if c.Caps["STARTTLS"] {
		_, err = mc.waitFor(c.StartTLS(&tls.Config{
			InsecureSkipVerify: mc.conf.SkipCertificateVerification,
		}))
	}
	// Identify this client at the IMAP server
	if c.Caps["ID"] {
		_, err = mc.waitFor(c.ID("name", "watney"))
	}
	return c, err
}
Пример #8
0
//use imap to delete a mail
func (email *Email) DeleteEmail(w rest.ResponseWriter, r *rest.Request) {
	log.Printf("delete email...")
	addr := r.FormValue("imapAddr")
	//port := r.FormValue("smtpPort")
	user := r.FormValue("user")
	pwd := r.FormValue("pwd")
	id := r.FormValue("id")

	//check params, return error

	//create imap client
	var (
		c   *imap.Client
		cmd *imap.Command
		rsp *imap.Response
	)

	// Connect to the server
	c, _ = imap.Dial(addr)

	// Remember to log out and close the connection when finished
	defer c.Logout(30 * time.Second)

	// Print server greeting (first response in the unilateral server data queue)
	log.Printf("Server says hello:%s", c.Data[0].Info)
	c.Data = nil

	// Enable encryption, if supported by the server
	if c.Caps["STARTTLS"] {
		c.StartTLS(nil)
	}

	// Authenticate
	if c.State() == imap.Login {
		c.Login(user, pwd)
	}

	// List all top-level mailboxes, wait for the command to finish
	cmd, _ = imap.Wait(c.List("", "%"))

	// Print mailbox information
	log.Printf("\nTop-level mailboxes:")
	for _, rsp = range cmd.Data {
		log.Printf("|--%s", rsp.MailboxInfo())
	}

	// Check for new unilateral server data responses
	for _, rsp = range c.Data {
		log.Printf("Server data:%s", rsp)
	}
	c.Data = nil

	// Open a mailbox (synchronous command - no need for imap.Wait)
	c.Select("INBOX", true)
	log.Printf("\nMailbox status:%s\n", c.Mailbox)
	if c.Mailbox == nil {
		resp := EmailJsonResponse{Success: true}
		w.WriteJson(&resp)
		return
	}

	//use Expunge to delete a mail
	set, _ := imap.NewSeqSet("")
	mid, _ := strconv.Atoi(id)
	set.AddNum(uint32(mid))

	//delete mail
	cmd, err := c.Expunge(set)
	if err != nil {
		log.Printf("%v ", cmd)
	} else {
		log.Printf("delete mail ok")
	}

}
Пример #9
0
func (emaill *Email) getEmailContentUseIMAP(w rest.ResponseWriter, r *rest.Request) {
	addr := r.FormValue("imapAddr")
	port := r.FormValue("imapPort")
	user := r.FormValue("user")
	pwd := r.FormValue("pwd")
	id := r.FormValue("id")

	address := addr + ":" + port
	log.Printf("get email content use imap %s\n", address)

	var (
		c   *imap.Client
		cmd *imap.Command
		rsp *imap.Response
	)

	// Connect to the server
	c, err := imap.Dial(addr)
	if err != nil {
		log.Printf("dial %s error\n", address)
		return
	}

	// Remember to log out and close the connection when finished
	defer c.Logout(30 * time.Second)

	// Print server greeting (first response in the unilateral server data queue)
	log.Printf("Server says hello:%s", c.Data[0].Info)
	c.Data = nil

	// Enable encryption, if supported by the server
	if c.Caps["STARTTLS"] {
		c.StartTLS(nil)
	}

	// Authenticate
	if c.State() == imap.Login {
		c.Login(user, pwd)
	}

	// List all top-level mailboxes, wait for the command to finish
	cmd, _ = imap.Wait(c.List("", "%"))

	// Print mailbox information
	log.Printf("\nTop-level mailboxes:")
	for _, rsp = range cmd.Data {
		log.Printf("|--%s", rsp.MailboxInfo())
	}

	// Check for new unilateral server data responses
	for _, rsp = range c.Data {
		log.Printf("Server data:%s", rsp)
	}
	c.Data = nil

	// Open a mailbox (synchronous command - no need for imap.Wait)
	c.Select("INBOX", true)
	log.Printf("\nMailbox status:%s\n", c.Mailbox)
	if c.Mailbox == nil {
		resp := EmailJsonResponse{Success: true}
		w.WriteJson(&resp)
		return
	}

	// Fetch the headers of the 10 most recent messages
	set, _ := imap.NewSeqSet("")
	set.Add(id)
	// if c.Mailbox.Messages >= 10 {
	// 	set.AddRange(c.Mailbox.Messages-9, c.Mailbox.Messages) //测试只取最新一封邮件
	// } else {
	// 	set.Add("1:*")
	// }
	cmd, _ = c.Fetch(set, "RFC822.HEADER", "RFC822.TEXT") //指定要获取的内容

	// Process responses while the command is running
	log.Printf("\nget mail [%s] messages:", id)
	for cmd.InProgress() {
		// Wait for the next response (no timeout)
		c.Recv(-1)

		// Process command data
		for _, rsp = range cmd.Data {
			header := imap.AsBytes(rsp.MessageInfo().Attrs["RFC822.HEADER"])
			if msg, _ := mail.ReadMessage(bytes.NewReader(header)); msg != nil {
				subject := msg.Header.Get("Subject")
				log.Printf("|--%s", subject)

				realSubject := GetRealSubject(subject)
				log.Printf("in rest_email.go: get real subject")
				log.Printf(realSubject)

				senderAddr := msg.Header.Get("From")
				recverAddrList := msg.Header.Get("To")

				realSenderAddr := GetRealSubject(senderAddr)
				realRecverAddrList := GetRealSubject(recverAddrList)

				body := imap.AsBytes(rsp.MessageInfo().Attrs["RFC822.TEXT"])
				//log.Printf("email body: %s", body)
				//realBody  := GetRealBody(string(body))
				headerAndBody := make([]byte, len(header)+len(body))
				copy(headerAndBody, header)
				copy(headerAndBody[len(header):], body)

				msg, _ := mail.ReadMessage(bytes.NewReader(headerAndBody))
				mime, _ := enmime.ParseMIMEBody(msg)
				realBody := mime.Text //如果原始内容为html,会去掉html元素标签
				log.Printf("real body: %s", realBody)

				//获取MIMEPart所有节点内容
				// log.Printf("root ======================")
				// root := mime.Root
				// if root != nil {
				// 	log.Printf(string(root.Content()))
				// 	log.Printf("child==========")
				// 	if child := root.FirstChild(); child != nil {
				// 		log.Printf(string(child.Content()))
				// 	}

				// }

				attachments := mime.Attachments
				log.Printf("attachments len=%d", len(attachments))
				count := len(attachments)
				var attachmentList []Attachment = nil
				var data EmailContent
				if count > 0 {
					attachmentList = make([]Attachment, count)
					for i := 0; i < len(attachments); i++ {
						name := attachments[i].FileName()
						content := attachments[i].Content() //todo encode by base64
						log.Printf("name===%s", name)
						attachmentList[i] = Attachment{Name: name, Body: string(content)}
					}

				}
				data = EmailContent{Subject: realSubject, SenderAddr: realSenderAddr,
					RecverAddrList: realRecverAddrList, Content: realBody,
					Attachments: attachmentList}

				resp := EmailJsonResponse{Success: true, Data: data}
				w.WriteJson(resp)
			}
		}
		cmd.Data = nil

		// Process unilateral server data
		for _, rsp = range c.Data {
			log.Printf("Server data:%s", rsp)
		}
		c.Data = nil
	}

	// Check command completion status
	if rsp, err := cmd.Result(imap.OK); err != nil {
		if err == imap.ErrAborted {
			log.Printf("Fetch command aborted\n")
		} else {
			log.Printf("Fetch error:%s\n", rsp.Info)
		}
	}

}
Пример #10
0
func main() {
	token := flag.String("token", "", "The Telegram bot token")
	to := flag.String("to", "", "The mail recipient")
	from := flag.String("from", "", "The mail sender")
	server := flag.String("server", "", "The mail server")
	port := flag.Int("port", 587, "The mail server port")
	user := flag.String("user", "", "")
	pass := flag.String("pass", "", "")
	subject := flag.String("subject", "", "")

	flag.Parse()

	bot, err := telebot.NewBot(*token)
	if err != nil {
		return
	}

	// Fetching Mails and send as Telegram messages

	var (
		c   *imap.Client
		cmd *imap.Command
		rsp *imap.Response
	)

	c, _ = imap.Dial(*server)

	defer c.Logout(30 * time.Second)

	c.Data = nil

	if c.Caps["STARTTLS"] {
		c.StartTLS(nil)
	}

	if c.State() == imap.Login {
		c.Login(*user, *pass)
	}

	cmd, _ = imap.Wait(c.List("", "%"))

	c.Data = nil

	c.Select("INBOX", true)

	set, _ := imap.NewSeqSet("")
	set.Add("1:*")
	cmd, _ = c.Fetch(set, "RFC822.HEADER")

	for cmd.InProgress() {
		c.Recv(-1)

		for _, rsp = range cmd.Data {
			header := imap.AsBytes(rsp.MessageInfo().Attrs["RFC822.HEADER"])
			if msg, _ := mail.ReadMessage(bytes.NewReader(header)); msg != nil {
				fmt.Println("|--", msg.Header.Get("FROM"))
			}
		}
		cmd.Data = nil
		c.Data = nil
	}

	if rsp, err := cmd.Result(imap.OK); err != nil {
		if err == imap.ErrAborted {
			fmt.Println("Fetch command aborted")
		} else {
			fmt.Println("Fetch error:", rsp.Info)
		}
	}

	/*
	 * Listen to Telegram messages and send as mail
	 */

	messages := make(chan telebot.Message)
	bot.Listen(messages, 1*time.Second)

	for message := range messages {

		m := gomail.NewMessage()
		m.SetHeader("From", *from)
		m.SetHeader("To", *to)
		m.SetHeader("Subject", *subject)
		m.SetBody("text/html", message.Text)

		d := gomail.NewPlainDialer(*server, *port, *user, *pass)
		d.TLSConfig = &tls.Config{InsecureSkipVerify: true}

		if err := d.DialAndSend(m); err != nil {
			panic(err)
		}
	}
}
Пример #11
0
// Fetch email for the specified user and host.
func Fetch(host, user, pass string) {
	c, err := imap.Dial(host)
	if err != nil {
		log.Print(err)
		return
	}
	defer c.Logout(30 * time.Second)

	log.Println("Server says hello:", c.Data[0].Info)
	c.Data = nil

	if c.Caps["STARTTLS"] {
		c.StartTLS(nil)
	}

	if c.State() == imap.Login {
		c.Login(user, pass)
	}

	cmd, err := imap.Wait(c.List("", "%"))
	if err != nil {
		log.Print(err)
		return
	}

	log.Println("\nTop-level mailboxes:")
	for _, rsp := range cmd.Data {
		log.Println("|--", rsp.MailboxInfo())
	}

	for _, rsp := range c.Data {
		log.Println("Server data:", rsp)
	}
	c.Data = nil

	c.Select("INBOX", true)
	log.Print("\nMailbox status:\n", c.Mailbox)

	set, _ := imap.NewSeqSet("")
	if c.Mailbox.Messages >= 10 {
		set.AddRange(c.Mailbox.Messages-9, c.Mailbox.Messages)
	} else {
		set.Add("1:*")
	}
	cmd, _ = c.Fetch(set, "RFC822.HEADER")

	log.Println("\nMost recent messages:")
	for cmd.InProgress() {
		// Wait for the next response (no timeout)
		c.Recv(-1)

		// Process command data
		for _, rsp := range cmd.Data {
			header := imap.AsBytes(rsp.MessageInfo().Attrs["RFC822.HEADER"])
			if msg, _ := mail.ReadMessage(bytes.NewReader(header)); msg != nil {
				log.Println("|--", msg.Header.Get("Subject"))
			}
		}
		cmd.Data = nil

		// Process unilateral server data
		for _, rsp := range c.Data {
			log.Println("Server data:", rsp)
		}
		c.Data = nil
	}

	if rsp, err := cmd.Result(imap.OK); err != nil {
		if err == imap.ErrAborted {
			log.Println("Fetch command aborted")
		} else {
			log.Println("Fetch error:", rsp.Info)
		}
	}
}
Пример #12
0
func ExampleClient() {
	//
	// Note: most of error handling code is omitted for brevity
	//
	var (
		c   *imap.Client
		cmd *imap.Command
		rsp *imap.Response
	)

	// Connect to the server
	c, _ = imap.Dial("imap.example.com")

	// Remember to log out and close the connection when finished
	defer c.Logout(30 * time.Second)

	// Print server greeting (first response in the unilateral server data queue)
	fmt.Println("Server says hello:", c.Data[0].Info)
	c.Data = nil

	// Enable encryption, if supported by the server
	if c.Caps["STARTTLS"] {
		c.StartTLS(nil)
	}

	// Authenticate
	if c.State() == imap.Login {
		c.Login("*****@*****.**", "mysupersecretpassword")
	}

	// List all top-level mailboxes, wait for the command to finish
	cmd, _ = imap.Wait(c.List("", "%"))

	// Print mailbox information
	fmt.Println("\nTop-level mailboxes:")
	for _, rsp = range cmd.Data {
		fmt.Println("|--", rsp.MailboxInfo())
	}

	// Check for new unilateral server data responses
	for _, rsp = range c.Data {
		fmt.Println("Server data:", rsp)
	}
	c.Data = nil

	// Open a mailbox (synchronous command - no need for imap.Wait)
	c.Select("INBOX", true)
	fmt.Print("\nMailbox status:\n", c.Mailbox)

	// Fetch the headers of the 10 most recent messages
	set, _ := imap.NewSeqSet("")
	if c.Mailbox.Messages >= 10 {
		set.AddRange(c.Mailbox.Messages-9, c.Mailbox.Messages)
	} else {
		set.Add("1:*")
	}
	cmd, _ = c.Fetch(set, "RFC822.HEADER")

	// Process responses while the command is running
	fmt.Println("\nMost recent messages:")
	for cmd.InProgress() {
		// Wait for the next response (no timeout)
		c.Recv(-1)

		// Process command data
		for _, rsp = range cmd.Data {
			header := imap.AsBytes(rsp.MessageInfo().Attrs["RFC822.HEADER"])
			if msg, _ := mail.ReadMessage(bytes.NewReader(header)); msg != nil {
				fmt.Println("|--", msg.Header.Get("Subject"))
			}
		}
		cmd.Data = nil

		// Process unilateral server data
		for _, rsp = range c.Data {
			fmt.Println("Server data:", rsp)
		}
		c.Data = nil
	}

	// Check command completion status
	if rsp, err := cmd.Result(imap.OK); err != nil {
		if err == imap.ErrAborted {
			fmt.Println("Fetch command aborted")
		} else {
			fmt.Println("Fetch error:", rsp.Info)
		}
	}
}