Other languages
Go, Ruby, PHP, Java, C#, and anything else: the API over plain HTTPS.
There is nothing special about the SDKs. The API is JSON over HTTPS with a bearer token, so any language with an HTTP client is a first-class client. The examples below all do the same thing: send one message. Everything else in /docs/rest works the same way.
Go
package main
import (
"bytes"
"encoding/json"
"net/http"
"os"
)
func main() {
body, _ := json.Marshal(map[string]any{
"to": []string{"jane@acme.com"},
"subject": "Your quote",
"body": "Attached, as promised.",
})
req, _ := http.NewRequest("POST", "https://mcpmailer.com/v1/messages", bytes.NewReader(body))
req.Header.Set("Authorization", "Bearer "+os.Getenv("MCPMAILER_API_KEY"))
req.Header.Set("Content-Type", "application/json")
res, err := http.DefaultClient.Do(req)
if err != nil {
panic(err)
}
defer res.Body.Close()
}Ruby
require "net/http"
require "json"
uri = URI("https://mcpmailer.com/v1/messages")
res = Net::HTTP.post(uri, {
to: ["jane@acme.com"],
subject: "Your quote",
body: "Attached, as promised."
}.to_json, {
"Authorization" => "Bearer #{ENV['MCPMAILER_API_KEY']}",
"Content-Type" => "application/json"
})
puts JSON.parse(res.body)["messageId"]PHP
<?php
$res = file_get_contents('https://mcpmailer.com/v1/messages', false, stream_context_create([
'http' => [
'method' => 'POST',
'header' => "Authorization: Bearer " . getenv('MCPMAILER_API_KEY') . "\r\n" .
"Content-Type: application/json\r\n",
'content' => json_encode([
'to' => ['jane@acme.com'],
'subject' => 'Your quote',
'body' => 'Attached, as promised.',
]),
],
]));
echo json_decode($res, true)['messageId'];Anything else
Java, C#, Rust, Elixir, and the rest follow the same three rules: POST JSON, set the Authorization header, and read the status field on the response. /openapi.json is a complete OpenAPI 3.1 description, so a generated client is a reasonable option too.
curl https://mcpmailer.com/v1/messages \
-H "Authorization: Bearer mmk_live_..." \
-H "Content-Type: application/json" \
-d '{
"to": ["ada@example.com"],
"subject": "Shipping update",
"body": "The parts landed this morning."
}'A 200 means the message went out. A 422 with a status field is a refusal you can act on, not a transport failure, so treat it as a result and read reason. A 429 carries retry-after in seconds.
{
"status": "sent",
"messageId": "msg_01J9X8Q2K7"
}