Skip to content
John Koisch edited this page Mar 24, 2014 · 12 revisions

Overview

MFA stands for Multi-Factor Authentication, which many banks and financial institutions use to verify the identity of their users.

An example would be for the user to log into the bank via their desktop browser, whence the bank sends a code via SMS to their registered mobile device. This code must be entered into the website to access their bank information.

Plaid and MFA

Plaid modulates the banks' usage of MFA through their API. This results in the need to manage your user flow when accessing the Plaid API. This gem provides several workflows to help you do this.

Initiating User Flow

The Plaid flow requires that you hit the standard connect method

  • client = Plaid.client 'plaid_test','plaid_good','chase'
  • x = client.connect

How this gem handles the MFA return

Because Chase is an institution that requires an MFA flow, the return and the client will have several pieces of information about the MFA required by Chase.

  • x.http_code <= 201
  • x.mfa_type <= "device"
  • x.is_mfa? <= true
  • x.message <= "MFA: Code sent to t..t@plaid.com"; this indicates the access code was sent to an email
  • x.access_token <= the unique access token for this user that you will need to access information later in the flow

So much for the response. But there is also some information that the client stores as part of managing the workflow.

  • client.access_token <= the same access token as in the response
  • client.mfa_type <= set from the last response, in this case "device"
  • client.mfa_message <= set from the last response, see x.message above
  • client.is_mfa? <= set from the last response, in this case "true"
  • client.mfa_response <= an array of all of the MFA responses that this client has been involved in

Why put it in two places? Well, sometimes it makes sense to look at the response, and sometimes you want to handle things in a client object.

Handling the response to the MFA request

Let us assume that the response to the MFA question is "1234".

  • x = client.connect_step "1234"

Note that the gem handles sorting the request parameters out for you, so the access_token is implicitly managed in the above call. At any rate, "x" is a response object that you can use to access the information normally.

  • x.accounts <= the array of accounts associated with the user's accounts at Chase

Note that our client object's state has been updated:

  • client.mfa_type <= nil
  • client.mfa_message <= nil
  • client.is_mfa? <= false
  • client.mfa_response <= keeps the history, in this case the above response to client.connect

These reflect that the last call to Plaid left us with useful and no need to re-submit MFA information.

Idealized flow

This is, more or less, what you will be doing in your app.

  • client = Plaid.client 'plaid_test','me@example.com','plaid_good','chase'
  • x = client.connect_init_user
  • ==> To check for MFA, you may want to test for response types, e.g., if x.http_code == 200 or you may want to test for whether the connection requires MFA, e.g. if client.is_mfa? etc.
  • ==> To check for errors, You can test for the object, e.g., if x.is_a? PlaidError, elsif x.is_a? PlaidResponse, or the message.
  • x = client.connect_step "48288"
  • ==> you will want to check for an error again, but assuming that you are good, you can wait to get the webhook notification
  • thin_client = Plaid.thin_client "me@example.com", "chase", client.account_token.to_s
  • x = thin_client.followup
  • x.accounts.each do |acct|
  • do_something_with_the_info(acct)
  • end

There are other branches to this flow that the Plaid gem helps you handle, including getting listings of MFA modes, multi-question answers, not using a webhook to receive Plaid notifications, and so on. Once you get through MFA, Plaid is pretty clean in terms of how you grab these information sets. The Plaid gem just tries to make things work a little easier for a customer.