مراية لـ
https://github.com/postalserver/postal.git
تم المزامنة 2026-01-17 13:39:46 +00:00
style(rubocop): fix all safe auto correctable offenses
هذا الالتزام موجود في:
@@ -1,19 +1,19 @@
|
||||
authenticator :server do
|
||||
friendly_name "Server Authenticator"
|
||||
header "X-Server-API-Key", "The API token for a server that you wish to authenticate with.", :example => 'f29a45f0d4e1744ebaee'
|
||||
error 'InvalidServerAPIKey', "The API token provided in X-Server-API-Key was not valid.", :attributes => {:token => "The token that was looked up"}
|
||||
error 'ServerSuspended', "The mail server has been suspended"
|
||||
header "X-Server-API-Key", "The API token for a server that you wish to authenticate with.", example: "f29a45f0d4e1744ebaee"
|
||||
error "InvalidServerAPIKey", "The API token provided in X-Server-API-Key was not valid.", attributes: { token: "The token that was looked up" }
|
||||
error "ServerSuspended", "The mail server has been suspended"
|
||||
lookup do
|
||||
if key = request.headers['X-Server-API-Key']
|
||||
if credential = Credential.where(:type => 'API', :key => key).first
|
||||
if key = request.headers["X-Server-API-Key"]
|
||||
if credential = Credential.where(type: "API", key: key).first
|
||||
if credential.server.suspended?
|
||||
error 'ServerSuspended'
|
||||
error "ServerSuspended"
|
||||
else
|
||||
credential.use
|
||||
credential
|
||||
end
|
||||
else
|
||||
error 'InvalidServerAPIKey', :token => key
|
||||
error "InvalidServerAPIKey", token: key
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
@@ -6,35 +6,34 @@ controller :messages do
|
||||
action :message do
|
||||
title "Return message details"
|
||||
description "Returns all details about a message"
|
||||
param :id, "The ID of the message", :type => Integer, :required => true
|
||||
returns Hash, :structure => :message, :structure_opts => {:paramable => {:expansions => false}}
|
||||
error 'MessageNotFound', "No message found matching provided ID", :attributes => {:id => "The ID of the message"}
|
||||
param :id, "The ID of the message", type: Integer, required: true
|
||||
returns Hash, structure: :message, structure_opts: { paramable: { expansions: false } }
|
||||
error "MessageNotFound", "No message found matching provided ID", attributes: { id: "The ID of the message" }
|
||||
action do
|
||||
begin
|
||||
message = identity.server.message(params.id)
|
||||
rescue Postal::MessageDB::Message::NotFound => e
|
||||
error 'MessageNotFound', :id => params.id
|
||||
error "MessageNotFound", id: params.id
|
||||
end
|
||||
structure :message, message, :return => true
|
||||
structure :message, message, return: true
|
||||
end
|
||||
end
|
||||
|
||||
action :deliveries do
|
||||
title "Return deliveries for a message"
|
||||
description "Returns an array of deliveries which have been attempted for this message"
|
||||
param :id, "The ID of the message", :type => Integer, :required => true
|
||||
returns Array, :structure => :delivery, :structure_opts => {:full => true}
|
||||
error 'MessageNotFound', "No message found matching provided ID", :attributes => {:id => "The ID of the message"}
|
||||
param :id, "The ID of the message", type: Integer, required: true
|
||||
returns Array, structure: :delivery, structure_opts: { full: true }
|
||||
error "MessageNotFound", "No message found matching provided ID", attributes: { id: "The ID of the message" }
|
||||
action do
|
||||
begin
|
||||
message = identity.server.message(params.id)
|
||||
rescue Postal::MessageDB::Message::NotFound => e
|
||||
error 'MessageNotFound', :id => params.id
|
||||
error "MessageNotFound", id: params.id
|
||||
end
|
||||
message.deliveries.map do |d|
|
||||
structure :delivery, d
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
@@ -7,30 +7,30 @@ controller :send do
|
||||
title "Send a message"
|
||||
description "This action allows you to send a message by providing the appropriate options"
|
||||
# Acceptable Parameters
|
||||
param :to, "The e-mail addresses of the recipients (max 50)", :type => Array
|
||||
param :cc, "The e-mail addresses of any CC contacts (max 50)", :type => Array
|
||||
param :bcc, "The e-mail addresses of any BCC contacts (max 50)", :type => Array
|
||||
param :from, "The e-mail address for the From header", :type => String
|
||||
param :sender, "The e-mail address for the Sender header", :type => String
|
||||
param :subject, "The subject of the e-mail", :type => String
|
||||
param :tag, "The tag of the e-mail", :type => String
|
||||
param :reply_to, "Set the reply-to address for the mail", :type => String
|
||||
param :plain_body, "The plain text body of the e-mail", :type => String
|
||||
param :html_body, "The HTML body of the e-mail", :type => String
|
||||
param :attachments, "An array of attachments for this e-mail", :type => Array
|
||||
param :headers, "A hash of additional headers", :type => Hash
|
||||
param :bounce, "Is this message a bounce?", :type => :boolean
|
||||
param :to, "The e-mail addresses of the recipients (max 50)", type: Array
|
||||
param :cc, "The e-mail addresses of any CC contacts (max 50)", type: Array
|
||||
param :bcc, "The e-mail addresses of any BCC contacts (max 50)", type: Array
|
||||
param :from, "The e-mail address for the From header", type: String
|
||||
param :sender, "The e-mail address for the Sender header", type: String
|
||||
param :subject, "The subject of the e-mail", type: String
|
||||
param :tag, "The tag of the e-mail", type: String
|
||||
param :reply_to, "Set the reply-to address for the mail", type: String
|
||||
param :plain_body, "The plain text body of the e-mail", type: String
|
||||
param :html_body, "The HTML body of the e-mail", type: String
|
||||
param :attachments, "An array of attachments for this e-mail", type: Array
|
||||
param :headers, "A hash of additional headers", type: Hash
|
||||
param :bounce, "Is this message a bounce?", type: :boolean
|
||||
# Errors
|
||||
error 'ValidationError', "The provided data was not sufficient to send an email", :attributes => {:errors => "A hash of error details"}
|
||||
error 'NoRecipients', "There are no recipients defined to receive this message"
|
||||
error 'NoContent', "There is no content defined for this e-mail"
|
||||
error 'TooManyToAddresses', "The maximum number of To addresses has been reached (maximum 50)"
|
||||
error 'TooManyCCAddresses', "The maximum number of CC addresses has been reached (maximum 50)"
|
||||
error 'TooManyBCCAddresses', "The maximum number of BCC addresses has been reached (maximum 50)"
|
||||
error 'FromAddressMissing', "The From address is missing and is required"
|
||||
error 'UnauthenticatedFromAddress', "The From address is not authorised to send mail from this server"
|
||||
error 'AttachmentMissingName', "An attachment is missing a name"
|
||||
error 'AttachmentMissingData', "An attachment is missing data"
|
||||
error "ValidationError", "The provided data was not sufficient to send an email", attributes: { errors: "A hash of error details" }
|
||||
error "NoRecipients", "There are no recipients defined to receive this message"
|
||||
error "NoContent", "There is no content defined for this e-mail"
|
||||
error "TooManyToAddresses", "The maximum number of To addresses has been reached (maximum 50)"
|
||||
error "TooManyCCAddresses", "The maximum number of CC addresses has been reached (maximum 50)"
|
||||
error "TooManyBCCAddresses", "The maximum number of BCC addresses has been reached (maximum 50)"
|
||||
error "FromAddressMissing", "The From address is missing and is required"
|
||||
error "UnauthenticatedFromAddress", "The From address is not authorised to send mail from this server"
|
||||
error "AttachmentMissingName", "An attachment is missing a name"
|
||||
error "AttachmentMissingData", "An attachment is missing data"
|
||||
# Return
|
||||
returns Hash
|
||||
# Action
|
||||
@@ -51,13 +51,14 @@ controller :send do
|
||||
attributes[:attachments] = []
|
||||
(params.attachments || []).each do |attachment|
|
||||
next unless attachment.is_a?(Hash)
|
||||
attributes[:attachments] << {:name => attachment['name'], :content_type => attachment['content_type'], :data => attachment['data'], :base64 => true}
|
||||
|
||||
attributes[:attachments] << { name: attachment["name"], content_type: attachment["content_type"], data: attachment["data"], base64: true }
|
||||
end
|
||||
message = OutgoingMessagePrototype.new(identity.server, request.ip, 'api', attributes)
|
||||
message = OutgoingMessagePrototype.new(identity.server, request.ip, "api", attributes)
|
||||
message.credential = identity
|
||||
if message.valid?
|
||||
result = message.create_messages
|
||||
{:message_id => message.message_id, :messages => result}
|
||||
{ message_id: message.message_id, messages: result }
|
||||
else
|
||||
error message.errors.first
|
||||
end
|
||||
@@ -67,44 +68,43 @@ controller :send do
|
||||
action :raw do
|
||||
title "Send a raw RFC2882 message"
|
||||
description "This action allows you to send us a raw RFC2822 formatted message along with the recipients that it should be sent to. This is similar to sending a message through our SMTP service."
|
||||
param :mail_from, "The address that should be logged as sending the message", :type => String, :required => true
|
||||
param :rcpt_to, "The addresses this message should be sent to", :type => Array, :required => true
|
||||
param :data, "A base64 encoded RFC2822 message to send", :type => String, :required => true
|
||||
param :bounce, "Is this message a bounce?", :type => :boolean
|
||||
param :mail_from, "The address that should be logged as sending the message", type: String, required: true
|
||||
param :rcpt_to, "The addresses this message should be sent to", type: Array, required: true
|
||||
param :data, "A base64 encoded RFC2822 message to send", type: String, required: true
|
||||
param :bounce, "Is this message a bounce?", type: :boolean
|
||||
returns Hash
|
||||
error 'UnauthenticatedFromAddress', "The From address is not authorised to send mail from this server"
|
||||
error "UnauthenticatedFromAddress", "The From address is not authorised to send mail from this server"
|
||||
action do
|
||||
# Decode the raw message
|
||||
raw_message = Base64.decode64(params.data)
|
||||
|
||||
# Parse through mail to get the from/sender headers
|
||||
mail = Mail.new(raw_message.split("\r\n\r\n", 2).first)
|
||||
from_headers = {'from' => mail.from, 'sender' => mail.sender}
|
||||
from_headers = { "from" => mail.from, "sender" => mail.sender }
|
||||
authenticated_domain = identity.server.find_authenticated_domain_from_headers(from_headers)
|
||||
|
||||
# If we're not authenticated, don't continue
|
||||
if authenticated_domain.nil?
|
||||
error 'UnauthenticatedFromAddress'
|
||||
error "UnauthenticatedFromAddress"
|
||||
end
|
||||
|
||||
# Store the result ready to return
|
||||
result = {:message_id => nil, :messages => {}}
|
||||
result = { message_id: nil, messages: {} }
|
||||
params.rcpt_to.uniq.each do |rcpt_to|
|
||||
message = identity.server.message_db.new_message
|
||||
message.rcpt_to = rcpt_to
|
||||
message.mail_from = params.mail_from
|
||||
message.raw_message = raw_message
|
||||
message.received_with_ssl = true
|
||||
message.scope = 'outgoing'
|
||||
message.scope = "outgoing"
|
||||
message.domain_id = authenticated_domain.id
|
||||
message.credential_id = identity.id
|
||||
message.bounce = params.bounce ? 1 : 0
|
||||
message.save
|
||||
result[:message_id] = message.message_id if result[:message_id].nil?
|
||||
result[:messages][rcpt_to] = {:id => message.id, :token => message.token}
|
||||
result[:messages][rcpt_to] = { id: message.id, token: message.token }
|
||||
end
|
||||
result
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
@@ -2,9 +2,9 @@ structure :delivery do
|
||||
basic :id
|
||||
basic :status
|
||||
basic :details
|
||||
basic :output, :value => proc { o.output&.strip }
|
||||
basic :sent_with_ssl, :value => proc { o.sent_with_ssl == 1 }
|
||||
basic :output, value: proc { o.output&.strip }
|
||||
basic :sent_with_ssl, value: proc { o.sent_with_ssl == 1 }
|
||||
basic :log_id
|
||||
basic :time, :value => proc { o.time&.to_f }
|
||||
basic :timestamp, :value => proc { o.timestamp.to_f }
|
||||
basic :time, value: proc { o.time&.to_f }
|
||||
basic :timestamp, value: proc { o.timestamp.to_f }
|
||||
end
|
||||
|
||||
@@ -2,65 +2,65 @@ structure :message do
|
||||
basic :id
|
||||
basic :token
|
||||
|
||||
expansion(:status) {
|
||||
expansion(:status) do
|
||||
{
|
||||
:status => o.status,
|
||||
:last_delivery_attempt => o.last_delivery_attempt ? o.last_delivery_attempt.to_f : nil,
|
||||
:held => o.held == 1 ? true : false,
|
||||
:hold_expiry => o.hold_expiry ? o.hold_expiry.to_f : nil
|
||||
status: o.status,
|
||||
last_delivery_attempt: o.last_delivery_attempt ? o.last_delivery_attempt.to_f : nil,
|
||||
held: o.held == 1,
|
||||
hold_expiry: o.hold_expiry ? o.hold_expiry.to_f : nil
|
||||
}
|
||||
}
|
||||
end
|
||||
|
||||
expansion(:details) {
|
||||
expansion(:details) do
|
||||
{
|
||||
:rcpt_to => o.rcpt_to,
|
||||
:mail_from => o.mail_from,
|
||||
:subject => o.subject,
|
||||
:message_id => o.message_id,
|
||||
:timestamp => o.timestamp.to_f,
|
||||
:direction => o.scope,
|
||||
:size => o.size,
|
||||
:bounce => o.bounce,
|
||||
:bounce_for_id => o.bounce_for_id,
|
||||
:tag => o.tag,
|
||||
:received_with_ssl => o.received_with_ssl
|
||||
rcpt_to: o.rcpt_to,
|
||||
mail_from: o.mail_from,
|
||||
subject: o.subject,
|
||||
message_id: o.message_id,
|
||||
timestamp: o.timestamp.to_f,
|
||||
direction: o.scope,
|
||||
size: o.size,
|
||||
bounce: o.bounce,
|
||||
bounce_for_id: o.bounce_for_id,
|
||||
tag: o.tag,
|
||||
received_with_ssl: o.received_with_ssl
|
||||
}
|
||||
}
|
||||
end
|
||||
|
||||
expansion(:inspection) {
|
||||
expansion(:inspection) do
|
||||
{
|
||||
:inspected => o.inspected == 1 ? true : false,
|
||||
:spam => o.spam == 1 ? true : false,
|
||||
:spam_score => o.spam_score.to_f,
|
||||
:threat => o.threat == 1 ? true : false,
|
||||
:threat_details => o.threat_details
|
||||
inspected: o.inspected == 1,
|
||||
spam: o.spam == 1,
|
||||
spam_score: o.spam_score.to_f,
|
||||
threat: o.threat == 1,
|
||||
threat_details: o.threat_details
|
||||
}
|
||||
}
|
||||
end
|
||||
|
||||
expansion(:plain_body) { o.plain_body }
|
||||
|
||||
expansion(:html_body) { o.html_body }
|
||||
|
||||
expansion(:attachments) {
|
||||
expansion(:attachments) do
|
||||
o.attachments.map do |attachment|
|
||||
{
|
||||
:filename => attachment.filename.to_s,
|
||||
:content_type => attachment.mime_type,
|
||||
:data => Base64.encode64(attachment.body.to_s),
|
||||
:size => attachment.body.to_s.bytesize,
|
||||
:hash => Digest::SHA1.hexdigest(attachment.body.to_s)
|
||||
filename: attachment.filename.to_s,
|
||||
content_type: attachment.mime_type,
|
||||
data: Base64.encode64(attachment.body.to_s),
|
||||
size: attachment.body.to_s.bytesize,
|
||||
hash: Digest::SHA1.hexdigest(attachment.body.to_s)
|
||||
}
|
||||
end
|
||||
}
|
||||
end
|
||||
|
||||
expansion(:headers) { o.headers }
|
||||
|
||||
expansion(:raw_message) { Base64.encode64(o.raw_message) }
|
||||
|
||||
expansion(:activity_entries) {
|
||||
|
||||
expansion(:activity_entries) do
|
||||
{
|
||||
:loads => o.loads,
|
||||
:clicks => o.clicks
|
||||
loads: o.loads,
|
||||
clicks: o.clicks
|
||||
}
|
||||
}
|
||||
end
|
||||
end
|
||||
|
||||
المرجع في مشكلة جديدة
حظر مستخدم