CURL Mail Request

var mail = new CurlMail("sender@example.org",
                           to=["to@example.org"], cc=["bob@example.org"])

mail.headers_body["Content-Type:"] = """text/html; charset="UTF-8""""
mail.headers_body["Content-Transfer-Encoding:"] = "quoted-printable"

mail.body = "<h1>Here you can write HTML stuff.</h1>"
mail.subject = "Hello From My Nit Program"

# Set mail server
var error = mail.set_outgoing_server("smtps://smtp.example.org:465",
                                     "user@example.org", "mypassword")
if error != null then
    print "Mail Server Error: {error}"
    exit 0
end

# Send
error = mail.execute
if error != null then
    print "Transfer Error: {error}"
    exit 0
end

Introduced properties

fun bcc: nullable Array[String]

curl :: CurlMail :: bcc

BCC recipients (hidden from other recipients)
fun bcc=(bcc: nullable Array[String])

curl :: CurlMail :: bcc=

BCC recipients (hidden from other recipients)
fun body: nullable String

curl :: CurlMail :: body

Text content
fun body=(body: nullable String)

curl :: CurlMail :: body=

Text content
fun cc: nullable Array[String]

curl :: CurlMail :: cc

CC recipients
fun cc=(cc: nullable Array[String])

curl :: CurlMail :: cc=

CC recipients
init defaultinit(from: nullable String, to: nullable Array[String], subject: nullable String, body: nullable String, cc: nullable Array[String], bcc: nullable Array[String])

curl :: CurlMail :: defaultinit

fun execute: nullable CurlResponseFailed

curl :: CurlMail :: execute

Execute Mail request with settings configured through attribute
fun from: nullable String

curl :: CurlMail :: from

Address of the sender
fun from=(from: nullable String)

curl :: CurlMail :: from=

Address of the sender
fun headers: HeaderMap

curl :: CurlMail :: headers

HTTP header
fun headers=(headers: HeaderMap)

curl :: CurlMail :: headers=

HTTP header
fun headers_body: HeaderMap

curl :: CurlMail :: headers_body

Content header
fun headers_body=(headers_body: HeaderMap)

curl :: CurlMail :: headers_body=

Content header
fun set_outgoing_server(host: String, user: nullable String, pwd: nullable String): nullable CurlResponseFailed

curl :: CurlMail :: set_outgoing_server

Configure server host and user credentials if needed.
fun subject: nullable String

curl :: CurlMail :: subject

Subject line
fun subject=(subject: nullable String)

curl :: CurlMail :: subject=

Subject line
fun supported_outgoing_protocol: Array[String]

curl :: CurlMail :: supported_outgoing_protocol

Protocols supported to send mail to a server
protected fun supported_outgoing_protocol=(supported_outgoing_protocol: Array[String])

curl :: CurlMail :: supported_outgoing_protocol=

Protocols supported to send mail to a server
fun to: nullable Array[String]

curl :: CurlMail :: to

Main recipients
fun to=(to: nullable Array[String])

curl :: CurlMail :: to=

Main recipients

Redefined properties

redef type SELF: CurlMail

curl $ CurlMail :: SELF

Type of this instance, automatically specialized in every class

All properties

fun !=(other: nullable Object): Bool

core :: Object :: !=

Have self and other different values?
fun ==(other: nullable Object): Bool

core :: Object :: ==

Have self and other the same value?
type CLASS: Class[SELF]

core :: Object :: CLASS

The type of the class of self.
type SELF: Object

core :: Object :: SELF

Type of this instance, automatically specialized in every class
fun bcc: nullable Array[String]

curl :: CurlMail :: bcc

BCC recipients (hidden from other recipients)
fun bcc=(bcc: nullable Array[String])

curl :: CurlMail :: bcc=

BCC recipients (hidden from other recipients)
fun body: nullable String

curl :: CurlMail :: body

Text content
fun body=(body: nullable String)

curl :: CurlMail :: body=

Text content
fun cc: nullable Array[String]

curl :: CurlMail :: cc

CC recipients
fun cc=(cc: nullable Array[String])

curl :: CurlMail :: cc=

CC recipients
protected fun class_factory(name: String): CLASS

core :: Object :: class_factory

Implementation used by get_class to create the specific class.
fun class_name: String

core :: Object :: class_name

The class name of the object.
fun close

curl :: CurlRequest :: close

Close low-level resources associated to this request
init defaultinit(from: nullable String, to: nullable Array[String], subject: nullable String, body: nullable String, cc: nullable Array[String], bcc: nullable Array[String])

curl :: CurlMail :: defaultinit

fun execute: nullable CurlResponseFailed

curl :: CurlMail :: execute

Execute Mail request with settings configured through attribute
fun from: nullable String

curl :: CurlMail :: from

Address of the sender
fun from=(from: nullable String)

curl :: CurlMail :: from=

Address of the sender
fun get_class: CLASS

core :: Object :: get_class

The meta-object representing the dynamic type of self.
fun hash: Int

core :: Object :: hash

The hash code of the object.
fun headers: HeaderMap

curl :: CurlMail :: headers

HTTP header
fun headers=(headers: HeaderMap)

curl :: CurlMail :: headers=

HTTP header
fun headers_body: HeaderMap

curl :: CurlMail :: headers_body

Content header
fun headers_body=(headers_body: HeaderMap)

curl :: CurlMail :: headers_body=

Content header
init init

core :: Object :: init

fun inspect: String

core :: Object :: inspect

Developer readable representation of self.
protected fun inspect_head: String

core :: Object :: inspect_head

Return "CLASSNAME:#OBJECTID".
intern fun is_same_instance(other: nullable Object): Bool

core :: Object :: is_same_instance

Return true if self and other are the same instance (i.e. same identity).
fun is_same_serialized(other: nullable Object): Bool

core :: Object :: is_same_serialized

Is self the same as other in a serialization context?
intern fun is_same_type(other: Object): Bool

core :: Object :: is_same_type

Return true if self and other have the same dynamic type.
intern fun object_id: Int

core :: Object :: object_id

An internal hash code for the object based on its identity.
fun output

core :: Object :: output

Display self on stdout (debug only).
intern fun output_class_name

core :: Object :: output_class_name

Display class name on stdout (debug only).
fun serialization_hash: Int

core :: Object :: serialization_hash

Hash value use for serialization
fun set_outgoing_server(host: String, user: nullable String, pwd: nullable String): nullable CurlResponseFailed

curl :: CurlMail :: set_outgoing_server

Configure server host and user credentials if needed.
fun subject: nullable String

curl :: CurlMail :: subject

Subject line
fun subject=(subject: nullable String)

curl :: CurlMail :: subject=

Subject line
fun supported_outgoing_protocol: Array[String]

curl :: CurlMail :: supported_outgoing_protocol

Protocols supported to send mail to a server
protected fun supported_outgoing_protocol=(supported_outgoing_protocol: Array[String])

curl :: CurlMail :: supported_outgoing_protocol=

Protocols supported to send mail to a server
intern fun sys: Sys

core :: Object :: sys

Return the global sys object, the only instance of the Sys class.
fun to: nullable Array[String]

curl :: CurlMail :: to

Main recipients
fun to=(to: nullable Array[String])

curl :: CurlMail :: to=

Main recipients
abstract fun to_jvalue(env: JniEnv): JValue

core :: Object :: to_jvalue

fun to_s: String

core :: Object :: to_s

User readable representation of self.
fun verbose: Bool

curl :: CurlRequest :: verbose

Shall this request be verbose?
fun verbose=(verbose: Bool)

curl :: CurlRequest :: verbose=

Shall this request be verbose?
package_diagram curl::CurlMail CurlMail curl::CurlRequest CurlRequest curl::CurlMail->curl::CurlRequest curl::NativeCurlCallbacks NativeCurlCallbacks curl::CurlMail->curl::NativeCurlCallbacks core::Object Object curl::CurlRequest->core::Object curl::NativeCurlCallbacks->core::Object ...core::Object ... ...core::Object->core::Object

Ancestors

interface Object

core :: Object

The root of the class hierarchy.

Parents

class CurlRequest

curl :: CurlRequest

CURL Request
interface NativeCurlCallbacks

curl :: NativeCurlCallbacks

Interface for internal information callbacks methods

Class definitions

curl $ CurlMail
# CURL Mail Request
#
# ~~~
# # Craft mail
# var mail = new CurlMail("sender@example.org",
#                            to=["to@example.org"], cc=["bob@example.org"])
#
# mail.headers_body["Content-Type:"] = """text/html; charset="UTF-8""""
# mail.headers_body["Content-Transfer-Encoding:"] = "quoted-printable"
#
# mail.body = "<h1>Here you can write HTML stuff.</h1>"
# mail.subject = "Hello From My Nit Program"
#
# # Set mail server
# var error = mail.set_outgoing_server("smtps://smtp.example.org:465",
#                                      "user@example.org", "mypassword")
# if error != null then
#     print "Mail Server Error: {error}"
#     exit 0
# end
#
# # Send
# error = mail.execute
# if error != null then
#     print "Transfer Error: {error}"
#     exit 0
# end
# ~~~
class CurlMail
	super CurlRequest
	super NativeCurlCallbacks

	# Address of the sender
	var from: nullable String is writable

	# Main recipients
	var to: nullable Array[String] is writable

	# Subject line
	var subject: nullable String is writable

	# Text content
	var body: nullable String is writable

	# CC recipients
	var cc: nullable Array[String] is writable

	# BCC recipients (hidden from other recipients)
	var bcc: nullable Array[String] is writable

	# HTTP header
	var headers = new HeaderMap is lazy, writable

	# Content header
	var headers_body = new HeaderMap is lazy, writable

	# Protocols supported to send mail to a server
	#
	# Default value at `["smtp", "smtps"]`
	var supported_outgoing_protocol = ["smtp", "smtps"]

	# Helper method to add pair values to mail content while building it (ex: "To:", "address@mail.com")
	private fun add_pair_to_content(str: String, att: String, val: nullable String): String
	do
		if val != null then return "{str}{att}{val}\n"
		return "{str}{att}\n"
	end

	# Helper method to add entire list of pairs to mail content
	private fun add_pairs_to_content(content: String, pairs: HeaderMap): String
	do
		for h_key, h_val in pairs do content = add_pair_to_content(content, h_key, h_val)
		return content
	end

	# Check for host and protocol availability
	private fun is_supported_outgoing_protocol(host: String): CURLCode
	do
		var host_reach = host.split_with("://")
		if host_reach.length > 1 and supported_outgoing_protocol.has(host_reach[0]) then return once new CURLCode.ok
		return once new CURLCode.unsupported_protocol
	end

	# Configure server host and user credentials if needed.
	fun set_outgoing_server(host: String, user: nullable String, pwd: nullable String): nullable CurlResponseFailed
	do
		# Check Curl initialisation
		if not self.curl.is_ok then return answer_failure(0, "Curl instance is not correctly initialized")

		var err

		# Host & Protocol
		err = is_supported_outgoing_protocol(host)
		if not err.is_ok then return answer_failure(err.to_i, err.to_s)

		err = self.curl.native.easy_setopt(new CURLOption.url, host)
		if not err.is_ok then return answer_failure(err.to_i, err.to_s)

		# Credentials
		if not user == null and not pwd == null then
			err = self.curl.native.easy_setopt(new CURLOption.username, user)
			if not err.is_ok then return answer_failure(err.to_i, err.to_s)

			err = self.curl.native.easy_setopt(new CURLOption.password, pwd)
			if not err.is_ok then return answer_failure(err.to_i, err.to_s)
		end

		return null
	end

	# Execute Mail request with settings configured through attribute
	fun execute: nullable CurlResponseFailed
	do
		if not self.curl.is_ok then return answer_failure(0, "Curl instance is not correctly initialized")

		var lines = new Array[String]

		# Headers
		var headers = self.headers
		if not headers.is_empty then
			for k, v in headers do lines.add "{k}{v}"
		end

		# Recipients
		var all_recipients = new Array[String]
		var to = self.to
		if to != null and to.length > 0 then
			lines.add "To:{to.join(",")}"
			all_recipients.append to
		end

		var cc = self.cc
		if cc != null and cc.length > 0 then
			lines.add "Cc:{cc.join(",")}"
			all_recipients.append cc
		end

		var bcc = self.bcc
		if bcc != null and bcc.length > 0 then all_recipients.append bcc

		if all_recipients.is_empty then return answer_failure(0, "There must be at lease one recipient")

		var err = self.curl.native.easy_setopt(new CURLOption.follow_location, 1)
		if not err.is_ok then return answer_failure(err.to_i, err.to_s)

		err = self.curl.native.easy_setopt(new CURLOption.mail_rcpt, all_recipients.to_curlslist)
		if not err.is_ok then return answer_failure(err.to_i, err.to_s)

		# From
		var from = self.from
		if not from == null then
			lines.add "From:{from}"

			err = self.curl.native.easy_setopt(new CURLOption.mail_from, from)
			if not err.is_ok then return answer_failure(err.to_i, err.to_s)
		end

		# Subject
		var subject = self.subject
		if subject == null then subject = "" # Default
		lines.add "Subject: {subject}"

		# Headers body
		var headers_body = self.headers_body
		if not headers_body.is_empty then
			for k, v in headers_body do lines.add "{k}{v}"
		end

		# Body
		var body = self.body
		if body == null then body = "" # Default

		lines.add ""
		lines.add body
		lines.add ""

		err = self.curl.native.register_callback_read(self)
		if not err.is_ok then return answer_failure(err.to_i, err.to_s)

		var content = lines.join("\n")
		err = self.curl.native.register_read_datas_callback(self, content)
		if not err.is_ok then return answer_failure(err.to_i, err.to_s)

		var err_resp = perform
		if err_resp != null then return err_resp

		return null
	end
end
lib/curl/curl.nit:337,1--525,3