This page explains how to authenticate users to your Nylas application using IMAP auth. IMAP connections don’t require a provider auth app, and they don’t include calendar functionality.
For more information about working with IMAP accounts in Nylas, see Use IMAP accounts and data with Nylas.
New options for Yahoo, Exchange, and iCloud users
If you’re authenticating Yahoo, Exchange on-prem, or iCloud users, you can either connect them using IMAP auth or use the dedicated Nylas connectors for those providers. If you authenticate them using IMAP, you can access email data only, even if the service also provides calendar features.
If you plan to authenticate Yahoo users, you should use the new v3 Yahoo OAuth method instead of IMAP auth to improve reliability.
Create an IMAP connector
You can create an IMAP connector in the v3 Dashboard, using the Nylas APIs, or using the Nylas SDKs.
Create an IMAP connector in v3 Dashboard
To create an IMAP connector in the Nylas Dashboard, first navigate to the Nylas application you’re creating the connector for. Then, click Connectors in the left navigation, find the IMAP tile, and click Add.
Create an IMAP connector using APIs
Make a POST /v3/connectors
request and set provider
to imap
to create an IMAP connector.
curl --request POST \ --url https://api.us.nylas.com/v3/connectors \ --header 'Content-Type: application/json' \ --header 'Accept: application/json, application/gzip' \ --header 'Authorization: Bearer <NYLAS_API_KEY>' \ --data '{ "provider": "imap" }'
Create an IMAP connector using Nylas SDKs
The following examples show how to create an IMAP connector using the Nylas SDKs.
import "dotenv/config";import Nylas from "nylas";
const config = { apiKey: process.env.NYLAS_API_KEY, apiUri: process.env.NYLAS_API_URI,};
const nylas = new Nylas(config);
async function createConnector() { try { const connector = await nylas.connectors.create({ requestBody: { provider: "imap", }, });
console.log("Connector created:", connector); } catch (error) { console.error("Error creating connector:", error); }}
createConnector();
from dotenv import load_dotenvload_dotenv()
import osimport sysfrom nylas import Client
nylas = Client( os.environ.get('NYLAS_API_KEY'), os.environ.get('NYLAS_API_URI'))
connector = nylas.connectors.create( request_body={ "provider": "imap" })
require 'nylas'
nylas = Nylas::Client.new(api_key: "<NYLAS_API_KEY>")
request_body = { provider: "imap"}
connector = nylas.connectors.create(request_body: request_body)
puts connector
import com.nylas.NylasClient;import com.nylas.models.*;
public class connector { public static void main(String[] args) throws NylasSdkTimeoutError, NylasApiError { NylasClient nylas = new NylasClient.Builder("<NYLAS_API_KEY>").build(); CreateConnectorRequest request = new CreateConnectorRequest.Imap();
nylas.connectors().create(request); }}
import com.nylas.NylasClientimport com.nylas.models.CreateConnectorRequest
fun main(args: Array<String>) { val nylas: NylasClient = NylasClient(apiKey = "<NYLAS_API_KEY>") val request : CreateConnectorRequest = CreateConnectorRequest.Imap();
nylas.connectors().create(request)}
Create grants for IMAP users
Most IMAP providers require that you use an application password to authenticate third-party tools. If this is the case, you need to redirect the user to their provider so they can enter their app password before authenticating. Some providers use the user’s usual login credentials and don’t require app passwords.
Nylas v3 offers Hosted OAuth and Custom Authentication for the supported IMAP providers.
Create an IMAP grant with Hosted OAuth
You can create IMAP grants using either Hosted OAuth with an API key or Hosted OAuth and an access token.
You can also start the Hosted Auth flow using the Nylas SDKs, as in the examples below.
import "dotenv/config";import express from "express";import Nylas from "nylas";
const config = { clientId: process.env.NYLAS_CLIENT_ID, clientSecret: process.env.NYLAS_CLIENT_SECRET, callbackUri: "http://localhost:3000/oauth/exchange", apiKey: process.env.NYLAS_API_KEY, apiUri: process.env.NYLAS_API_URI,};
const nylas = new Nylas({ apiKey: config.apiKey, apiUri: config.apiUri,});
const app = express();const port = 3000;
// Route to initialize authenticationapp.get("/nylas/auth", (req, res) => { const authUrl = nylas.auth.urlForOAuth2({ clientId: config.clientId, provider: "imap", redirectUri: config.redirectUri, loginHint: process.env.AOL_IMAP_USERNAME, state: "state", });
res.redirect(authUrl);});
// Callback route Nylas redirects toapp.get("/oauth/exchange", async (req, res) => { const code = req.query.code;
if (!code) { res.status(400).send("No authorization code returned from Nylas");
return; }
try { const response = await nylas.auth.exchangeCodeForToken({ clientId: config.clientId, redirectUri: config.redirectUri, code, });
const { grantId } = response;
res.status(200); } catch (error) { res.status(500).send("Failed to exchange authorization code for token"); }});
from dotenv import load_dotenvload_dotenv()
import jsonimport os
from functools import wrapsfrom io import BytesIOfrom flask import Flask, request, redirect, gfrom nylas import Client
nylas = Client( os.environ.get("NYLAS_CLIENT_ID"), os.environ.get("NYLAS_API_URI"))
REDIRECT_CLIENT_URI = 'http://localhost:9000/oauth/exchange'flask_app = Flask(__name__)@flask_app.route("/nylas/generate-auth-url", methods=["GET"])
def build_auth_url(): auth_url = nylas.auth.url_for_oauth2( config={ "client_id": os.environ.get("NYLAS_CLIENT_ID"), "provider": 'imap', "redirect_uri": REDIRECT_CLIENT_URI, "login_hint": os.environ.get("AOL_IMAP_USERNAME"), "state": "state", } )
return redirect(auth_url)
@flask_app.route("/oauth/exchange", methods=["GET"])def exchange_code_for_token(): code_exchange_response = nylas.auth.exchange_code_for_token( request={ "code": request.args.get('code'), "client_id": os.environ.get("NYLAS_CLIENT_ID"), "redirect_uri": REDIRECT_CLIENT_URI } )
return { 'email': code_exchange_response.email, 'grant_id': code_exchange_response.grant_id }
# frozen_string_literal: true
require 'nylas'require 'sinatra'
set :show_exceptions, :after_handler
error 404 do 'No authorization code returned from Nylas'end
error 500 do 'Failed to exchange authorization code for token'end
nylas = Nylas::Client.new(api_key: "<NYLAS_API_KEY>")
get '/nylas/auth' do config = { client_id: "<NYLAS_CLIENT_ID>", provider: 'imap', redirect_uri: 'http://localhost:4567/oauth/exchange', login_hint: '<AOL_IMAP_USER>', state: "<state>" }
url = nylas.auth.url_for_oauth2(config) redirect urlend
get '/oauth/exchange' do code = params[:code] status 404 if code.nil?
begin response = nylas.auth.exchange_code_for_token({ client_id: "<NYLAS_CLIENT_ID>", redirect_uri: 'http://localhost:4567/oauth/exchange', code: code }) rescue StandardError status 500 else puts response
grant_id = response[:grant_id] email = response[:email]
"Grant_Id: #{grant_id} \n Email: #{email}" endend
import java.util.*;import static spark.Spark.*;import com.nylas.NylasClient;import com.nylas.models.*;
public class AuthRequest { public static void main(String[] args) throws NylasSdkTimeoutError, NylasApiError { NylasClient nylas = new NylasClient.Builder("<NYLAS_API_KEY>").build();
get("/nylas/auth", (request, response) -> { List<String> scope = new ArrayList<>(); UrlForAuthenticationConfig config = new UrlForAuthenticationConfig( "<NYLAS_CLIENT_ID>", "http://localhost:4567/oauth/exchange", AccessType.ONLINE, AuthProvider.IMAP, Prompt.DETECT, scope, true, "sQ6vFQN",
String url = nylas.auth().urlForOAuth2(config);
response.redirect(url);
return null; });
get("/oauth/exchange", (request, response) -> { String code = request.queryParams("code");
if(code == null) { response.status(401);} assert code != null;
CodeExchangeRequest codeRequest = new CodeExchangeRequest( "http://localhost:4567/oauth/exchange", code, "<NYLAS_CLIENT_ID>", "nylas");
try { CodeExchangeResponse codeResponse = nylas.auth().exchangeCodeForToken(codeRequest);
return "%s".formatted(codeResponse); } catch(Exception e) { return "%s".formatted(e); } }); }}
import com.nylas.NylasClientimport com.nylas.models.AccessTypeimport com.nylas.models.AuthProviderimport com.nylas.models.Promptimport com.nylas.models.UrlForAuthenticationConfigimport spark.kotlin.Httpimport spark.kotlin.ignite
fun main(args: Array<String>) { val nylas: NylasClient = NylasClient(apiKey = "<NYLAS_API_KEY>") val http: Http = ignite()
http.get("/nylas/auth") { val scope = listOf("https://www.googleapis.com/auth/userinfo.email") val config : UrlForAuthenticationConfig = UrlForAuthenticationConfig( "<NYLAS_CLIENT_ID>", "http://localhost:4567/oauth/exchange", AccessType.ONLINE, AuthProvider.IMAP, Prompt.DETECT, scope, true, "sQ6vFQN", "<email_to_connect>")
val url = nylas.auth().urlForOAuth2(config)
response.redirect(url) }}
http.get("/oauth/exchange") { val code : String = request.queryParams("code")
if(code == "") { response.status(401) }
val codeRequest : CodeExchangeRequest = CodeExchangeRequest( "http://localhost:4567/oauth/exchange", code, "<NYLAS_CLIENT_ID>", "nylas" )
try { val codeResponse : CodeExchangeResponse = nylas.auth().exchangeCodeForToken(codeRequest) codeResponse } catch (e : Exception) { e }}
Create an IMAP grant with Custom Authentication
If you already have your user’s password or app password, you can create a grant for them using Custom Authentication.
The example below shows how to make a Custom Authentication request with the correct provider and settings. The rest of the authentication process follows the same process as for non-IMAP grant creation.
curl -X POST https://api.us.nylas.com/v3/connect/custom \ --header 'Authorization: Bearer <NYLAS_API_KEY>' \ --header 'Content-Type: application/json' \ --data-raw '{ "provider": "imap", "settings": { "imap_username": "<IMAP_USERNAME>", "imap_password": "<IMAP_PASSWORD>", "imap_host": "imap.mail.me.com", "imap_port": 993, "smtp_host": "smtp.mail.me.com", "smtp_port": 465 } }'
For more information, see the Custom auth documentation.
Error handling for IMAP Hosted authentication
Nylas creates a grant only if both the IMAP settings are validated and the provider accepts the end user’s login credentials. When an error occurs, the redirect_uri
includes an error_type
query parameter when the auth process is complete. The possible error_type
values are…
provider_not_responding
: The IMAP provider didn’t respond to the login request from Nylas.invalid_authentication
: The provider responded with an incorrect credential error. Nylas prompts the user with an error message.auth_limit_reached
: The user entered an incorrect password three times. Nylas redirects back to your application’sredirect_uri
with the error code instead of showing an error message.