> ## Documentation Index
> Fetch the complete documentation index at: https://rain-sandbox-trial.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

# Card Issuance

> Issue a virtual or physical card using the Rain SDK, from application submission through approval to card creation.

Issue a card end-to-end: submit an application, get it approved, and create the card.

## Prerequisites

Before you start, make sure you have:

* The SDK [installed and initialized](/sdks/overview)
* An API key from the [Developer Dashboard](/docs/set-up-access)
* Your [program type](/docs/first-steps) identified (Consumer vs. Corporate)

## Issue a card

Follow these steps to issue a virtual or physical card:

<Steps>
  <Step title="Submit an application">
    Create a KYC (Consumer) or KYB (Corporate) application for your customer.

    <CodeGroup>
      ```ts Consumer (TypeScript) theme={null}
      const application = await client.applications.user.create({
        accountPurpose: 'web3Payments',
        annualSalary: '50000-100000',
        expectedMonthlyVolume: '1000-5000',
        ipAddress: '203.0.113.1',
        isTermsOfServiceAccepted: true,
        occupation: '15-1252',
        firstName: 'Jane',
        lastName: 'Doe',
        email: 'jane@example.com',
        birthDate: '1990-01-15',
        nationalId: '123456789',
        countryOfIssue: 'US',
        address: {
          city: 'Austin',
          country: 'United States',
          countryCode: 'US',
          line1: '123 Main St',
          postalCode: '78701',
          region: 'TX',
        },
        walletAddress: '0x...', // required for Rain-managed programs
      });

      console.log(application.id); // save this for the next step
      ```

      ```go Consumer (Go) theme={null}
      package main

      import (
      	"context"
      	"fmt"

      	rainsdk "github.com/SignifyHQ/rain-sdk-go"
      	"github.com/SignifyHQ/rain-sdk-go/option"
      )

      func main() {
      	client := rainsdk.NewClient(option.WithAPIKey("YOUR_API_KEY"))

      	application, err := client.Applications.User.New(context.TODO(), rainsdk.ApplicationUserNewParams{
      		OfUsingAPI: &rainsdk.ApplicationUserNewParamsBodyUsingAPI{
      			AccountPurpose:           "web3Payments",
      			AnnualSalary:             "50000-100000",
      			ExpectedMonthlyVolume:    "1000-5000",
      			IPAddress:                "203.0.113.1",
      			IsTermsOfServiceAccepted: true,
      			Occupation:               "15-1252",
      			WalletAddress:            rainsdk.String("0x..."), // required for Rain-managed programs
      		},
      	})
      	if err != nil {
      		panic(err)
      	}

      	fmt.Println(application.ID) // save this for the next step
      }
      ```

      ```python Consumer (Python) theme={null}
      application = client.applications.user.create(
          account_purpose="web3Payments",
          annual_salary="50000-100000",
          expected_monthly_volume="1000-5000",
          ip_address="203.0.113.1",
          is_terms_of_service_accepted=True,
          occupation="15-1252",
          first_name="Jane",
          last_name="Doe",
          email="jane@example.com",
          birth_date="1990-01-15",
          national_id="123456789",
          country_of_issue="US",
          address={
              "city": "Austin",
              "country": "United States",
              "country_code": "US",
              "line1": "123 Main St",
              "postal_code": "78701",
              "region": "TX",
          },
          wallet_address="0x...",  # required for Rain-managed programs
      )

      print(application.id)  # save this for the next step
      ```

      ```ts Corporate (TypeScript) theme={null}
      const company = await client.applications.company.create({
        name: 'Acme Corp',
        address: {
          city: 'San Francisco',
          country: 'United States',
          countryCode: 'US',
          line1: '123 Market St',
          postalCode: '94105',
          region: 'CA',
        },
        entity: {
          name: 'Acme Corp LLC',
          registrationNumber: '123456789',
          taxId: '12-3456789',
          website: 'https://acme.com',
        },
        initialUser: {
          firstName: 'Jane',
          lastName: 'Doe',
          email: 'jane@acme.com',
          birthDate: '1990-01-01',
          countryOfIssue: 'US',
          nationalId: '123456789',
          address: {
            city: 'San Francisco',
            country: 'United States',
            countryCode: 'US',
            line1: '123 Market St',
            postalCode: '94105',
            region: 'CA',
          },
          walletAddress: '0x...',
          ipAddress: '203.0.113.1',
          isTermsOfServiceAccepted: true,
        },
        representatives: [],
        ultimateBeneficialOwners: [],
      });
      ```

      ```go Corporate (Go) theme={null}
      company, err := client.Applications.Company.New(context.TODO(), rainsdk.ApplicationCompanyNewParams{
      	Name: "Acme Corp",
      	Address: rainsdk.PhysicalAddressParam{
      		City:        "San Francisco",
      		Country:     "United States",
      		CountryCode: "US",
      		Line1:       "123 Market St",
      		PostalCode:  "94105",
      		Region:      "CA",
      	},
      	Entity: rainsdk.ApplicationCompanyNewParamsEntity{
      		Name:               "Acme Corp LLC",
      		RegistrationNumber: "123456789",
      		TaxID:              "12-3456789",
      		Website:            "https://acme.com",
      	},
      	InitialUser: rainsdk.ApplicationCompanyNewParamsInitialUser{
      		IPAddress:                "203.0.113.1",
      		IsTermsOfServiceAccepted: true,
      		WalletAddress:            rainsdk.String("0x..."),
      	},
      	Representatives:          []rainsdk.IssuingApplicationPersonParam{},
      	UltimateBeneficialOwners: []rainsdk.IssuingApplicationPersonParam{},
      })
      ```
    </CodeGroup>

    <Info>
      In sandbox, include `approved` in the user's last name (e.g., `"Doe approved"`) to automatically approve the application. See [Testing in Sandbox](/docs/simulating-transactions/overview) for more testing shortcuts.
    </Info>

    See [Signing Up a Customer](/docs/signing-up-a-customer) for the full workflow including document uploads and KYC provider share tokens.
  </Step>

  <Step title="Check application status">
    Poll the application status or listen for a [webhook](/docs/webhooks) notification.

    <CodeGroup>
      ```ts TypeScript theme={null}
      const status = await client.applications.user.retrieve(application.id);

      // Possible statuses: 'approved' | 'pending' | 'needsInformation'
      //   | 'needsVerification' | 'manualReview' | 'denied' | 'locked' | 'canceled'
      if (status.applicationStatus !== 'approved') {
        console.log(`Current status: ${status.applicationStatus}`);
      }
      ```

      ```go Go theme={null}
      status, err := client.Applications.User.Get(context.TODO(), application.ID)
      if err != nil {
      	panic(err)
      }

      if status.ApplicationStatus != rainsdk.IssuingApplicationApplicationStatusApproved {
      	fmt.Printf("Current status: %s\n", status.ApplicationStatus)
      }
      ```

      ```python Python theme={null}
      status = client.applications.user.retrieve(application.id)

      if status.application_status != "approved":
          print(f"Current status: {status.application_status}")
      ```
    </CodeGroup>

    See [Application States](/docs/application-states) for all possible statuses and transitions.
  </Step>

  <Step title="Create a card">
    Once the application is approved, issue a virtual or physical card for the user.

    <CodeGroup>
      ```ts Virtual (TypeScript) theme={null}
      const card = await client.users.createCard(application.id, {
        type: 'virtual',
        limit: {
          amount: 50000,            // $500.00 in cents
          frequency: 'per30DayPeriod',
        },
      });

      console.log(card.id, card.last4, card.status);
      ```

      ```go Virtual (Go) theme={null}
      card, err := client.Users.NewCard(context.TODO(), application.ID, rainsdk.UserNewCardParams{
      	Type: rainsdk.UserNewCardParamsTypeVirtual,
      	Limit: rainsdk.IssuingCardLimitParam{
      		Amount:    50000, // $500.00 in cents
      		Frequency: rainsdk.IssuingCardLimitFrequencyPer30DayPeriod,
      	},
      })
      if err != nil {
      	panic(err)
      }

      fmt.Println(card.ID, card.Last4, card.Status)
      ```

      ```python Virtual (Python) theme={null}
      card = client.users.create_card(
          application.id,
          type="virtual",
          limit={
              "amount": 50000,
              "frequency": "per30DayPeriod",
          },
      )

      print(card.id, card.last4, card.status)
      ```

      ```ts Physical (TypeScript) theme={null}
      const card = await client.users.createCard(application.id, {
        type: 'physical',
        shipping: {
          line1: '123 Main St',
          city: 'Austin',
          region: 'TX',
          postalCode: '78701',
          country: 'United States',
          countryCode: 'US',
          phoneNumber: '+15125551234',
          method: 'standard',
        },
      });
      ```

      ```go Physical (Go) theme={null}
      card, err := client.Users.NewCard(context.TODO(), application.ID, rainsdk.UserNewCardParams{
      	Type: rainsdk.UserNewCardParamsTypePhysical,
      	Shipping: rainsdk.UserNewCardParamsShipping{
      		PhysicalAddressParam: rainsdk.PhysicalAddressParam{
      			Line1:       "123 Main St",
      			City:        "Austin",
      			Region:      "TX",
      			PostalCode:  "78701",
      			Country:     "United States",
      			CountryCode: "US",
      		},
      		PhoneNumber: "+15125551234",
      		Method:      "standard",
      	},
      })
      ```
    </CodeGroup>

    See [Issuing Cards](/docs/issuing-cards) for spending limit options, display name rules, and shipping methods.
  </Step>

  <Step title="Retrieve card details">
    Fetch the card to confirm it was created:

    <CodeGroup>
      ```ts TypeScript theme={null}
      const card = await client.cards.retrieve(card.id);
      console.log(card.type, card.status, card.last4);
      ```

      ```go Go theme={null}
      card, err := client.Cards.Get(context.TODO(), card.ID)
      if err != nil {
      	panic(err)
      }
      fmt.Println(card.Type, card.Status, card.Last4)
      ```

      ```python Python theme={null}
      card = client.cards.retrieve(card.id)
      print(card.type, card.status, card.last4)
      ```
    </CodeGroup>

    To display the full PAN and CVC for virtual cards, decrypt the card secrets using an encrypted session. See [Viewing Encrypted Card Details](/docs/viewing-encrypted-card-details) for the full decryption flow.
  </Step>
</Steps>

## What's next

<Columns cols={3}>
  <Card title="Fund the Card" icon="wallet" href="/sdks/funding-and-transfers">
    Deposit collateral so the cardholder can start spending.
  </Card>

  <Card title="Issuing Cards" icon="credit-card" href="/docs/issuing-cards">
    Explore all card configuration options.
  </Card>

  <Card title="Test in Sandbox" icon="flask" href="/docs/simulating-transactions/overview">
    Simulate transactions before going live.
  </Card>
</Columns>
