GreenArrow Email Software Documentation

Mailgun-Compatible IP Pool API

GreenArrow CloudMTA

This feature is only available on GreenArrow CloudMTA.

Contact us

Contact us if you need support for a field or an API that is not listed here.

Overview

The Mailgun-compatible IP Pool API lets software that was written for Mailgun’s dedicated IP pool API read and create GreenArrow Routes. A Mailgun IP pool is a GreenArrow Route, and the IP addresses of a pool are the IP addresses of the Route. A Route that you create in another way (for example in the Engine UI or with the Routes API) is visible here.

GreenArrow assigns the IP addresses of a Route when it creates the Route. You cannot choose, add, remove, or move the IP addresses of a pool.

These endpoints are available:

Endpoint Purpose
GET /v3/ip_pools Get a list of IP pools
POST /v3/ip_pools Create an IP pool

Send each request to the hostname of the Mailgun compatibility API of your GreenArrow CloudMTA. The examples on this page use mg.api.example.com.

The Routes feature must be enabled on the GreenArrow installation. When it is not enabled, each endpoint on this page answers 404 with the message IP pools are not enabled on this GreenArrow installation.

Authentication

Authenticate with HTTP Basic authentication. The username is api, and the password is a GreenArrow API key.

curl -s --user "api:$API_KEY" "https://mg.api.example.com/v3/ip_pools"

A request with no credentials, with a username other than api, or with a key that is not valid gets a 401 response. Do not depend on the body of a 401 response; it can change in a later release.

Requests and Responses

Parameters

A parameter that this page does not list is ignored, as on Mailgun, in the query string and in the body. The exception is ips, which Create an IP Pool refuses.

An endpoint that takes form parameters reads them only from a multipart/form-data body, as Mailgun documents. These rules apply:

  • A body of another content type (for example JSON, application/x-www-form-urlencoded, or no body) gets a 400. Mailgun accepts some of these bodies.
  • A form parameter in the query string gets a 400. So does a form parameter that is sent as a file part.
  • A value that has a NUL character, or that is not valid UTF-8, gets a 400.
  • A body that is larger than 1 MiB (1,048,576 bytes, with the multipart framing) gets a 400. A body that is larger than 32 MiB can get a 502 with an HTML body.
  • A parameter that is sent more than once gives its first value, as on Mailgun.

Errors

An error response has a JSON body, except the plain-text 404 for a path that is not a path of the Mailgun API, and the 502 for a body that is larger than 32 MiB. Most error bodies have one field, message:

{"message": "IP pools are not enabled on this GreenArrow installation"}

A 401 for a request that has no credentials that can be read has another body, as on Mailgun:

{"Error": "unauthorized"}

Status Meaning
400 The request is not valid. The message says why.
401 The credentials are missing or not valid.
404 The Routes feature is not enabled, the path is not a path of the Mailgun API, or the path does not support the HTTP method of the request. As on Mailgun, a path that is not a path of the Mailgun API gets the plain-text body 404 page not found, and a wrong method gets {"error": "not found"}.
429 No IP addresses are available for a new pool. The message is No IP addresses are available for a new IP pool. Try again in 1 hour, or contact GreenArrow support., and the Retry-After header is 3600 (seconds).
500 GreenArrow could not handle the request, for example because it could not get IP addresses for a new pool. The message is GreenArrow backend error. Contact GreenArrow support.
501 The path is a path of the Mailgun API that GreenArrow does not implement.
502 The request body is larger than 32 MiB.

Use the status code to handle an error. Do not depend on the text of a message.

Common Fields

These are the fields of a pool in the responses on this page.

pool_id

string

The identifier of the pool: 24 hexadecimal characters, made from the id of the Route. See Identifiers.

name

string

The name of the Route.

description

string

The description of the Route. A Route with no description has "".

ips

array of strings

The IP addresses of the Route, in numeric order (10.0.0.9 comes before 10.0.0.10). These are the public addresses that GreenArrow assigned to the Route. A pool with no IP addresses has [].

is_linked

boolean

true if at least one Sending Domain that is not deleted uses the Route (its route attribute names the Route). Sending Domains whose sending is disabled, and Sending Domains whose DNS is not verified, count. A Mail Class that sends through the Route does not.

Get a List of IP Pools

Returns every IP pool. This is every Route that is not deleted.

GET /v3/ip_pools

Mailgun’s documentation: Get DIPPs.

Parameters

None.

Response

ip_pools

array of hashes

Every pool, in name order. The letter case of a name does not matter in this order. Mailgun’s list has no fixed order. An account with no pools has [].

Each pool has these fields:

description: see Common Fields.

ips: see Common Fields.

metadata: always {}. Mailgun gives metadata.assignments here. GreenArrow does not.

is_inherited: always false. GreenArrow has no subaccounts.

is_linked: see Common Fields.

name: see Common Fields.

pool_id: see Common Fields.

message

string

Always success.

Example

curl -s --user "api:$API_KEY" "https://mg.api.example.com/v3/ip_pools"

200 OK:

{
  "ip_pools": [
    {
      "pool_id": "387cb3220000000000000007",
      "name": "transactional",
      "description": "Transactional mail",
      "ips": ["203.0.113.10"],
      "metadata": {},
      "is_linked": true,
      "is_inherited": false
    }
  ],
  "message": "success"
}

Create an IP Pool

Creates a Route with the name and the description. GreenArrow assigns the Route one IP address before it answers. The answer comes after the Route is ready to use.

POST /v3/ip_pools

Mailgun’s documentation: Create a DIPP.

Form Parameters

Send these parameters in a multipart/form-data body (see Requests and Responses).

description

string

/

required

The description of the Route. A blank value (description=) is allowed and gives "". GreenArrow stores the text exactly as you send it, with the spaces and line breaks around it.

At most 10,240 characters. A character that takes more than one byte (for example é or 😀) counts as one character. Mailgun accepted the longer descriptions that we tested.

Mailgun accepts a request with no description parameter. GreenArrow answers 400 with the message description is required.

ip

string

Not supported. A request that has ip, also with a blank value, gets a 400 with the message ip is not supported: GreenArrow provisions pool addresses automatically, and no pool is created. Mailgun adds the IP addresses of the account that you name to the new pool.

name

string

/

required

The name of the Route. GreenArrow removes the spaces around the name. Mailgun keeps them.

GreenArrow has these rules for a name. Mailgun has none of them. A name that breaks a rule gets a 400 whose message names the rule:

  • The name cannot be blank. (Message: name cannot be blank.)
  • At most 180 characters.
  • Only the ASCII characters 0x20 to 0x7e, but not a comma, #, or @.
  • The name cannot be an integer (for example 12345 or -5).
  • The name cannot be the name of another pool that is not deleted. The letter case does not matter. (Message: name has already been taken.)

Mailgun accepts a request with no name parameter. GreenArrow answers 400 with the message name is required.

GreenArrow also refuses ips, which Mailgun does not document, with the message ips is not supported: GreenArrow provisions pool addresses automatically.

When the name and the description both break a rule, the message has both messages, joined with ; .

Response

message

string

Always success.

pool_id

string

The pool_id of the new pool. See Common Fields.

Errors

Status Message Cause
400 The request body must be multipart/form-data The body is not multipart/form-data.
400 no multipart boundary param in Content-Type The Content-Type has no boundary parameter. This is Mailgun’s message.
400 multipart: NextPart: EOF The body does not have the boundary of its Content-Type. This is Mailgun’s message.
400 The request body is not valid multipart/form-data The body cannot be read for another reason.
400 The request body is larger than 1 MiB The body is larger than 1 MiB.
400 <parameter> must be sent in the multipart/form-data body, not in the query string name or description is in the query string.
400 <parameter> must be a text field, not a file name or description is a file part.
400 <parameter> must be valid UTF-8 text with no NUL characters A value has a NUL character or is not valid UTF-8.
400 <parameter> is required There is no name or no description parameter.
400 ip is not supported: GreenArrow provisions pool addresses automatically The request has ip, in the body, in the query string, or as a file part. The same message names ips.
400 name <rule>, description <rule> The name or the description breaks a rule (see the parameters).
429 No IP addresses are available for a new IP pool. Try again in 1 hour, or contact GreenArrow support. No IP addresses are available. Try again after the Retry-After time.
500 GreenArrow backend error. Contact GreenArrow support. GreenArrow could not confirm that the pool was created.

If a create gets a 500, check the pool list before retrying. The Route may have been created even if its response was lost.

Example

curl -s --user "api:$API_KEY" -X POST "https://mg.api.example.com/v3/ip_pools" \
  -F name=transactional \
  -F 'description=Transactional mail'

200 OK:

{"message": "success", "pool_id": "387cb3220000000000000007"}

400 Bad Request when the request has ip:

{"message": "ip is not supported: GreenArrow provisions pool addresses automatically"}

Identifiers

A pool_id is 24 hexadecimal characters, as on Mailgun. GreenArrow makes it from the id of the Route: the first 8 characters are always 387cb322, and the last 16 characters are the id of the Route in hexadecimal. For example, Route 7 is the pool 387cb3220000000000000007.

To send a message through a pool, give its pool_id as o:sending-ip-pool to the Mailgun-Compatible Messages API.

Differences from Mailgun

  • The order of the list. GET /v3/ip_pools returns the pools in name order, with the letter case ignored. Mailgun’s list has no fixed order.
  • metadata. Each pool in the list has "metadata": {}. Mailgun gives metadata.assignments there.
  • is_inherited. It is always false, because GreenArrow has no subaccounts.
  • IP addresses. GreenArrow assigns the IP addresses of a pool when it creates the pool. You cannot add, remove, or move IP addresses. POST /v3/ip_pools refuses ip (and ips). A new Mailgun pool has no IP addresses; a new GreenArrow pool has one.
  • Required parameters. POST /v3/ip_pools requires name and description. Mailgun accepts a request without them.
  • Name rules. GreenArrow removes the spaces around a name, and refuses a blank name, a name of more than 180 characters, a name with other characters than ASCII 0x20 to 0x7e (or with a comma, #, or @), a name that is an integer, and the name of another pool. Mailgun has none of these rules.
  • Description limit. A description has at most 10,240 characters. Mailgun accepted the tested longer descriptions.
  • Request formats. The endpoints that take form parameters accept only a multipart/form-data body of at most 1 MiB, with the form parameters in the body. Mailgun also accepts other bodies, larger bodies, and form parameters in the query string or in a file part.
  • Errors. The text of an error message can differ from Mailgun’s, and when a request has more than one problem, GreenArrow can report a different one than Mailgun.

Copyright © 2012–2026 GreenArrow Email