# Verify Silent Network Auth Testing Guide

## Test SNA Today

[Get Started](/docs/verify/verify-sna-live-test-number)

Skip the 2-4 week wait for carrier approvals and get directly to testing SNA with your own mobile number using the new [Live Test Number](/docs/verify/verify-sna-live-test-number) feature.

Verify Silent Network Auth (SNA) allows you to confirm user possession of a mobile phone number without explicit user intervention by communicating directly with mobile carriers. Learn more about how it works with [SNA Overview](/docs/verify/sna), [SNA API Reference](/docs/verify/api/verification#start-new-verification-with-silent-network-auth), and [What is Silent Network Authentication? blog post](https://www.twilio.com/blog/silent-network-authentication-sna-overview).

In this guide, we will walk you through testing the entire SNA process step-by-step on your own mobile device without having to make any modifications to your mobile app.

## Set up

* [Create a Twilio Account](https://www.twilio.com/try-twilio)
  * Note your Account SID and Auth Token from the [Console](https://console.twilio.com/).
* [Request access](https://docs.google.com/forms/d/e/1FAIpQLSeEtqZ5bNs27DcTGnG1mx11-ZQUztNlw8nkskVlFRFwkf7xMA/viewform) to the API and Live Test Number feature. If there are no issues, access will be granted within 24 business hours.
* [Create a Verify Service](https://www.twilio.com/console/verify/services)
  * Note your Service SID from the [Verify Services tab in the Console](https://console.twilio.com/us1/develop/verify/services).
* You will need to use a smartphone associated with an approved carrier (e.g. an iPhone with a Verizon Wireless phone number)

You also have the option to test SNA without carrier approval or a valid Live Test Number. In this testing flow, use Twilio Region US1 for your requests to Start a New SNA Verification for any mobile number and Invoke the SNA URL as described in this guide. Note that requests made to regions outside US1 in this testing flow will fail. When you reach the Check the Verification Attempt result step, you will receive an expected error code.

## Step 1: Start a New SNA Verification

To begin, use the [Start New Verification endpoint](/docs/verify/api/verification#start-new-verification-with-silent-network-auth) with the parameter `channel=sna` to create a new SNA Verification.

Start a Verification With Silent Network Auth

```js
// Download the helper library from https://www.twilio.com/docs/node/install
const twilio = require("twilio"); // Or, for ESM: import twilio from "twilio";

// Find your Account SID and Auth Token at twilio.com/console
// and set the environment variables. See http://twil.io/secure
const accountSid = process.env.TWILIO_ACCOUNT_SID;
const authToken = process.env.TWILIO_AUTH_TOKEN;
const client = twilio(accountSid, authToken);

async function createVerification() {
  const verification = await client.verify.v2
    .services("VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa")
    .verifications.create({
      channel: "sna",
      to: "+15017122661",
    });

  console.log(verification.sid);
}

createVerification();
```

```python
# Download the helper library from https://www.twilio.com/docs/python/install
import os
from twilio.rest import Client

# Find your Account SID and Auth Token at twilio.com/console
# and set the environment variables. See http://twil.io/secure
account_sid = os.environ["TWILIO_ACCOUNT_SID"]
auth_token = os.environ["TWILIO_AUTH_TOKEN"]
client = Client(account_sid, auth_token)

verification = client.verify.v2.services(
    "VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"
).verifications.create(channel="sna", to="+15017122661")

print(verification.sid)
```

```csharp
// Install the C# / .NET helper library from twilio.com/docs/csharp/install

using System;
using Twilio;
using Twilio.Rest.Verify.V2.Service;
using System.Threading.Tasks;

class Program {
    public static async Task Main(string[] args) {
        // Find your Account SID and Auth Token at twilio.com/console
        // and set the environment variables. See http://twil.io/secure
        string accountSid = Environment.GetEnvironmentVariable("TWILIO_ACCOUNT_SID");
        string authToken = Environment.GetEnvironmentVariable("TWILIO_AUTH_TOKEN");

        TwilioClient.Init(accountSid, authToken);

        var verification = await VerificationResource.CreateAsync(
            channel: "sna",
            to: "+15017122661",
            pathServiceSid: "VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa");

        Console.WriteLine(verification.Sid);
    }
}
```

```java
// Install the Java helper library from twilio.com/docs/java/install

import com.twilio.Twilio;
import com.twilio.rest.verify.v2.service.Verification;

public class Example {
    // Find your Account SID and Auth Token at twilio.com/console
    // and set the environment variables. See http://twil.io/secure
    public static final String ACCOUNT_SID = System.getenv("TWILIO_ACCOUNT_SID");
    public static final String AUTH_TOKEN = System.getenv("TWILIO_AUTH_TOKEN");

    public static void main(String[] args) {
        Twilio.init(ACCOUNT_SID, AUTH_TOKEN);
        Verification verification =
            Verification.creator("VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa", "+15017122661", "sna").create();

        System.out.println(verification.getSid());
    }
}
```

```go
// Download the helper library from https://www.twilio.com/docs/go/install
package main

import (
	"fmt"
	"github.com/twilio/twilio-go"
	verify "github.com/twilio/twilio-go/rest/verify/v2"
	"os"
)

func main() {
	// Find your Account SID and Auth Token at twilio.com/console
	// and set the environment variables. See http://twil.io/secure
	// Make sure TWILIO_ACCOUNT_SID and TWILIO_AUTH_TOKEN exists in your environment
	client := twilio.NewRestClient()

	params := &verify.CreateVerificationParams{}
	params.SetChannel("sna")
	params.SetTo("+15017122661")

	resp, err := client.VerifyV2.CreateVerification("VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
		params)
	if err != nil {
		fmt.Println(err.Error())
		os.Exit(1)
	} else {
		if resp.Sid != nil {
			fmt.Println(*resp.Sid)
		} else {
			fmt.Println(resp.Sid)
		}
	}
}
```

```php
<?php

// Update the path below to your autoload.php,
// see https://getcomposer.org/doc/01-basic-usage.md
require_once "/path/to/vendor/autoload.php";

use Twilio\Rest\Client;

// Find your Account SID and Auth Token at twilio.com/console
// and set the environment variables. See http://twil.io/secure
$sid = getenv("TWILIO_ACCOUNT_SID");
$token = getenv("TWILIO_AUTH_TOKEN");
$twilio = new Client($sid, $token);

$verification = $twilio->verify->v2
    ->services("VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa")
    ->verifications->create(
        "+15017122661", // To
        "sna" // Channel
    );

print $verification->sid;
```

```ruby
# Download the helper library from https://www.twilio.com/docs/ruby/install
require 'twilio-ruby'

# Find your Account SID and Auth Token at twilio.com/console
# and set the environment variables. See http://twil.io/secure
account_sid = ENV['TWILIO_ACCOUNT_SID']
auth_token = ENV['TWILIO_AUTH_TOKEN']
@client = Twilio::REST::Client.new(account_sid, auth_token)

verification = @client
               .verify
               .v2
               .services('VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa')
               .verifications
               .create(
                 channel: 'sna',
                 to: '+15017122661'
               )

puts verification.sid
```

```bash
# Install the twilio-cli from https://twil.io/cli

twilio api:verify:v2:services:verifications:create \
   --service-sid VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa \
   --channel sna \
   --to +15017122661
```

```bash
curl -X POST "https://verify.twilio.com/v2/Services/VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa/Verifications" \
--data-urlencode "Channel=sna" \
--data-urlencode "To=+15017122661" \
-u $TWILIO_ACCOUNT_SID:$TWILIO_AUTH_TOKEN
```

```json
{
  "sid": "VEaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
  "service_sid": "VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
  "account_sid": "ACaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
  "to": "+15017122661",
  "channel": "sna",
  "status": "pending",
  "valid": false,
  "date_created": "2015-07-30T20:00:00Z",
  "date_updated": "2015-07-30T20:00:00Z",
  "lookup": {
    "carrier": {
      "mobile_country_code": "311",
      "type": "mobile",
      "error_code": null,
      "mobile_network_code": "180",
      "name": "T-Mobile USA, Inc."
    }
  },
  "amount": null,
  "payee": null,
  "send_code_attempts": [
    {
      "time": "2015-07-30T20:00:00Z",
      "channel": "sna",
      "attempt_sid": "VLaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"
    }
  ],
  "sna": {
    "url": "https://mi.dnlsrv.com/m/id/ANBByzx7?data=AAAglRRdNn02iTFWfDWwdTjOzM8o%2F6JB86fH%2Bt%2FFftUPj0pFA0u8%2FibWuYwzmMeMOtdTwYlsO8V%2FXF%2BJmngMhbeGKYhHeTOF2H9VrGEYKcEEklPxHgb5GgL3XtYa33j3lIU%2By6InvoV%2FowWHBzA0QeFPBh6vmJ8LoUPJqGE7q0PRz618Z4ym1AGq%2BaomSq9PlP4rCduv9Cmtxu%2FrvPSBwocs0GCWDE8seK8t9epmPQW7gwODxkAiKr9UxhJd9KvmBVuAQPf%2BoFQVo86USXkhXqTvUzB2bNUYY9FCy3CWgZFTOa1D3H1CVxf1eHzYIswNA7SmOzP%2FBX8g6%2B0hkzwMRkcit3gBNs4evAVJiqAgYvUlrtGwwv9bFx4X7jWSHY4%3D&cipherSalt=yANeDq09bwM38SJs"
  },
  "url": "https://verify.twilio.com/v2/Services/VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa/Verifications/VEaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"
}
```

Check your response from the Start New Verification endpoint for the `sna.url` property. The SNA URL is unique for every Verification Attempt, has a default time-to-live of 10 minutes, and can only be processed once. Once it has been called, it will not be valid anymore.

Note its value for use in the next step:

```json
"sna": {
     "url": "https://mi.dnlsrv.com/m/id/ANBByzx7?data=AAAglRRdNn02iTFWfDWwdTjOzM8o%2F6JB86fH%2Bt%2FFftUPj0pFA0u8%2FibWuYwzmMeMOtdTwYlsO8V%2FXF%2BJmngMhbeGKYhHeTOF2H9VrGEYKcEEklPxHgb5GgL3XtYa33j3lIU%2By6InvoV%2FowWHBzA0QeFPBh6vmJ8LoUPJqGE7q0PRz618Z4ym1AGq%2BaomSq9PlP4rCduv9Cmtxu%2FrvPSBwocs0GCWDE8seK8t9epmPQW7gwODxkAiKr9UxhJd9KvmBVuAQPf%2BoFQVo86USXkhXqTvUzB2bNUYY9FCy3CWgZFTOa1D3H1CVxf1eHzYIswNA7SmOzP%2FBX8g6%2B0hkzwMRkcit3gBNs4evAVJiqAgYvUlrtGwwv9bFx4X7jWSHY4%3D&cipherSalt=yANeDq09bwM38SJs"
}
```

## Step 2: Invoke the SNA URL

You can invoke the URL by sending it to yourself through either email or Slack following the \*special instructions\* below.

### How to send the SNA URL via email

Copy and paste the SNA URL and send it to yourself via email.

![Email with multiple encrypted URLs for SNA external testing.](https://docs-resources.prod.twilio.com/12ee938cc60c3176f49364d56ba911375713515f5511882ad1563b43a918e7bc.png)

Note: Some email clients have security features, such as Microsoft's [Safe Links](https://learn.microsoft.com/en-us/microsoft-365/security/office-365-security/safe-links?view=o365-worldwide), that scan and open any embedded URLs in the email. The SNA URL is a one-time URL and can be made invalid during such security processes. To work around this in testing, you can use an email client that does not have this kind of security feature or modify the SNA URL from `https://...` to `hxxps://...` so the URL is non-clickable and change it back to `https://...` when you're ready to invoke it on your device. Other mobile email clients do not display the URL, even though the email is received. However, if you forward the email, the URL will be displayed.

### How to send the SNA URL via Slack

To send the SNA URL in Slack, paste it into a preexisting code block. You must create a code block first because pasting the SNA URL directly into the message composer will cause Slack to automatically invalidate the URL.

![Slack message with a URL and encoded data string at 11:47 AM.](https://docs-resources.prod.twilio.com/723e94231ce14554b659c7f1a6ab4cb91799f181e06971bb6b111bb097d69dc3.png)

Create the empty code block using these keyboard shortcuts:

* Mac: Shift + Option + Command + C
* Windows: Ctrl + Alt + Shift + C

Then paste the SNA URL into the code block and send the message.

### Select the SNA URL

Before tapping the SNA URL, ensure that your mobile phone's Wi-Fi is turned off and that it is only using cellular data connection. Tap the SNA URL to continue the authentication process. It should open up in your default browser and after a processing time of four seconds or less, land on a screen that looks similar to this:

![Web browser showing URL mi.dnlsrv.com with message: ErrorCode=0, ErrorDescription=Success, Carrier=VZW.](https://docs-resources.prod.twilio.com/adce5ce5f1da6c67f907a365a6a0379402736253d29b3932b6859262f74a48bd.jpg)

You can now exit the browser, no further action is required with the response shown on this screen.

> \[!NOTE]
>
> In real implementations, invoke the SNA URL using a `POST` request.
>
> We recommend using a `POST` request for real implementations rather than a `GET` request as is happening in this example, although both HTTP methods will have the same end result. `POST` requests have increased security due to not being cached in HTTP caches or browser history.

## Step 3: Check the Verification Attempt result

> \[!WARNING]
>
> Verifications expire after a 10-minute window that begins after it's created.
>
> If you attempt to check a Verification that has expired then you will get a `404 Not Found` error. If you encounter this during testing, restart the flow by starting a new Verification.

Next, send a request to the [Verification Check API](/docs/verify/api/verification-check) to confirm that the SNA URL invocation and Verification Attempt were successful.

Check a Silent Network Auth Verification

```js
// Download the helper library from https://www.twilio.com/docs/node/install
const twilio = require("twilio"); // Or, for ESM: import twilio from "twilio";

// Find your Account SID and Auth Token at twilio.com/console
// and set the environment variables. See http://twil.io/secure
const accountSid = process.env.TWILIO_ACCOUNT_SID;
const authToken = process.env.TWILIO_AUTH_TOKEN;
const client = twilio(accountSid, authToken);

async function createVerificationCheck() {
  const verificationCheck = await client.verify.v2
    .services("VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa")
    .verificationChecks.create({ to: "+15017122661" });

  console.log(verificationCheck.sid);
}

createVerificationCheck();
```

```python
# Download the helper library from https://www.twilio.com/docs/python/install
import os
from twilio.rest import Client

# Find your Account SID and Auth Token at twilio.com/console
# and set the environment variables. See http://twil.io/secure
account_sid = os.environ["TWILIO_ACCOUNT_SID"]
auth_token = os.environ["TWILIO_AUTH_TOKEN"]
client = Client(account_sid, auth_token)

verification_check = client.verify.v2.services(
    "VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"
).verification_checks.create(to="+15017122661")

print(verification_check.sid)
```

```csharp
// Install the C# / .NET helper library from twilio.com/docs/csharp/install

using System;
using Twilio;
using Twilio.Rest.Verify.V2.Service;
using System.Threading.Tasks;

class Program {
    public static async Task Main(string[] args) {
        // Find your Account SID and Auth Token at twilio.com/console
        // and set the environment variables. See http://twil.io/secure
        string accountSid = Environment.GetEnvironmentVariable("TWILIO_ACCOUNT_SID");
        string authToken = Environment.GetEnvironmentVariable("TWILIO_AUTH_TOKEN");

        TwilioClient.Init(accountSid, authToken);

        var verificationCheck = await VerificationCheckResource.CreateAsync(
            to: "+15017122661", pathServiceSid: "VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa");

        Console.WriteLine(verificationCheck.Sid);
    }
}
```

```java
// Install the Java helper library from twilio.com/docs/java/install

import com.twilio.Twilio;
import com.twilio.rest.verify.v2.service.VerificationCheck;

public class Example {
    // Find your Account SID and Auth Token at twilio.com/console
    // and set the environment variables. See http://twil.io/secure
    public static final String ACCOUNT_SID = System.getenv("TWILIO_ACCOUNT_SID");
    public static final String AUTH_TOKEN = System.getenv("TWILIO_AUTH_TOKEN");

    public static void main(String[] args) {
        Twilio.init(ACCOUNT_SID, AUTH_TOKEN);
        VerificationCheck verificationCheck =
            VerificationCheck.creator("VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa").setTo("+15017122661").create();

        System.out.println(verificationCheck.getSid());
    }
}
```

```go
// Download the helper library from https://www.twilio.com/docs/go/install
package main

import (
	"fmt"
	"github.com/twilio/twilio-go"
	verify "github.com/twilio/twilio-go/rest/verify/v2"
	"os"
)

func main() {
	// Find your Account SID and Auth Token at twilio.com/console
	// and set the environment variables. See http://twil.io/secure
	// Make sure TWILIO_ACCOUNT_SID and TWILIO_AUTH_TOKEN exists in your environment
	client := twilio.NewRestClient()

	params := &verify.CreateVerificationCheckParams{}
	params.SetTo("+15017122661")

	resp, err := client.VerifyV2.CreateVerificationCheck("VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
		params)
	if err != nil {
		fmt.Println(err.Error())
		os.Exit(1)
	} else {
		if resp.Sid != nil {
			fmt.Println(*resp.Sid)
		} else {
			fmt.Println(resp.Sid)
		}
	}
}
```

```php
<?php

// Update the path below to your autoload.php,
// see https://getcomposer.org/doc/01-basic-usage.md
require_once "/path/to/vendor/autoload.php";

use Twilio\Rest\Client;

// Find your Account SID and Auth Token at twilio.com/console
// and set the environment variables. See http://twil.io/secure
$sid = getenv("TWILIO_ACCOUNT_SID");
$token = getenv("TWILIO_AUTH_TOKEN");
$twilio = new Client($sid, $token);

$verification_check = $twilio->verify->v2
    ->services("VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa")
    ->verificationChecks->create(["to" => "+15017122661"]);

print $verification_check->sid;
```

```ruby
# Download the helper library from https://www.twilio.com/docs/ruby/install
require 'twilio-ruby'

# Find your Account SID and Auth Token at twilio.com/console
# and set the environment variables. See http://twil.io/secure
account_sid = ENV['TWILIO_ACCOUNT_SID']
auth_token = ENV['TWILIO_AUTH_TOKEN']
@client = Twilio::REST::Client.new(account_sid, auth_token)

verification_check = @client
                     .verify
                     .v2
                     .services('VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa')
                     .verification_checks
                     .create(to: '+15017122661')

puts verification_check.sid
```

```bash
# Install the twilio-cli from https://twil.io/cli

twilio api:verify:v2:services:verification-check:create \
   --service-sid VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa \
   --to +15017122661
```

```bash
curl -X POST "https://verify.twilio.com/v2/Services/VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa/VerificationCheck" \
--data-urlencode "To=+15017122661" \
-u $TWILIO_ACCOUNT_SID:$TWILIO_AUTH_TOKEN
```

```json
{
  "sid": "VEaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
  "service_sid": "VAaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
  "account_sid": "ACaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
  "to": "+15017122661",
  "channel": "sms",
  "status": "approved",
  "valid": true,
  "amount": null,
  "payee": null,
  "sna_attempts_error_codes": [],
  "date_created": "2015-07-30T20:00:00Z",
  "date_updated": "2015-07-30T20:00:00Z"
}
```

Check your response from the Verification Check API for the `status` property. `approved` means that SNA successfully confirmed user possession of the mobile number provided.

```json
"status": { "approved" }
```

Check your response from the Verification Check API for the `sna_attempts_error_codes` property. If one or more errors occurred during the SNA process, you will see a list of error codes here. The `attempt_sid` property refers to the specific Verification Attempt that was created with the Start New Verification endpoint.

You can check the [Error and Warning Dictionary](/docs/api/errors) for more information on error codes including their possible causes and solutions.

```json
"sna_attempts_error_codes": [
    {
      "attempt_sid": "VLXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX",
      "code": 60001
    }
```
