FusionAuth developer image
FusionAuth developer logo
  • Back to site
  • Expert Advice
  • Blog
  • Developers
  • Downloads
  • Account
  • Contact sales
Navigate to...
  • Welcome
  • Getting Started
  • 5-Minute Setup Guide
  • Release Notes
  • Core Concepts
    • Overview
    • Users
    • Roles
    • Groups
    • Entity Management
    • Registrations
    • Applications
    • Tenants
    • Identity Providers
    • Key Master
    • SCIM
    • Search
    • Authentication and Authorization
    • Integration Points
    • Localization and Internationalization
    • Editions and Features
    • Roadmap
  • Installation Guide
    • Overview
    • System Requirements
    • Server Layout
    • Cloud
    • Cluster
    • Docker
    • Fast Path
    • Kubernetes
      • Overview
      • Deployment Guide
      • Minikube Setup
      • Amazon EKS Setup
      • Google GKE Setup
      • Microsoft AKS Setup
    • Kickstart™
    • Homebrew
    • Packages
    • Database
    • FusionAuth App
    • FusionAuth Search
    • Common Configuration
  • Admin Guide
    • Overview
    • Account Portal
    • Config Management
    • Licensing
    • Monitoring
    • Proxy Setup
    • Securing
    • Technical Support
    • Troubleshooting
    • Upgrading
  • Migration Guide
    • Overview
    • General
    • Auth0
    • Keycloak
    • Amazon Cognito
    • Firebase
    • Tutorial
  • APIs
    • Overview
    • Authentication
    • Errors
    • Actioning Users
    • API Keys
    • Applications
    • Audit Logs
    • Connectors
      • Overview
      • Generic
      • LDAP
    • Consents
    • Emails
    • Entity Management
      • Overview
      • Entities
      • Entity Types
      • Grants
    • Event Logs
    • Families
    • Forms
    • Form Fields
    • Groups
    • Identity Providers
      • Overview
      • Links
      • Apple
      • External JWT
      • Epic Games
      • Facebook
      • Google
      • HYPR
      • LinkedIn
      • Nintendo
      • OpenID Connect
      • SAML v2
      • SAML v2 IdP Initiated
      • Sony PlayStation Network
      • Steam
      • Twitch
      • Twitter
      • Xbox
    • Integrations
    • IP Access Control Lists
    • JWT
    • Keys
    • Lambdas
    • Login
    • Message Templates
    • Messengers
      • Overview
      • Generic
      • Kafka
      • Twilio
    • Multi-Factor/Two Factor
    • Passwordless
    • Reactor
    • Registrations
    • Reports
    • SCIM
      • Overview
      • SCIM EnterpriseUser
      • SCIM Group
      • SCIM Service Provider Config.
      • SCIM User
    • System
    • Tenants
    • Themes
    • Users
    • User Actions
    • User Action Reasons
    • User Comments
    • Webhooks
  • Client Libraries
    • Overview
    • Dart
    • Go
    • Java
    • JavaScript
    • .NET Core
    • Node
    • OpenAPI
    • PHP
    • Python
    • Ruby
    • Typescript
  • Themes
    • Overview
    • Examples
    • Helpers
    • Localization
    • Template Variables
  • Email & Templates
    • Overview
    • Configure Email
    • Email Templates
    • Email Variables
    • Message Templates
  • Events & Webhooks
    • Overview
    • Writing a Webhook
    • Securing Webhooks
    • Events
      • Overview
      • Audit Log Create
      • Event Log Create
      • JWT Public Key Update
      • JWT Refresh
      • JWT Refresh Token Revoke
      • Kickstart Success
      • User Action
      • User Bulk Create
      • User Create
      • User Create Complete
      • User Deactivate
      • User Delete
      • User Delete Complete
      • User Email Update
      • User Email Verified
      • User IdP Link
      • User IdP Unlink
      • User Login Failed
      • User Login Id Duplicate Create
      • User Login Id Duplicate Update
      • User Login New Device
      • User Login Success
      • User Login Suspicious
      • User Password Breach
      • User Password Reset Send
      • User Password Reset Start
      • User Password Reset Success
      • User Password Update
      • User Reactivate
      • User Registration Create
      • User Registration Create Complete
      • User Registration Delete
      • User Registration Delete Complete
      • User Registration Update
      • User Registration Update Complete
      • User Registration Verified
      • User Two Factor Method Add
      • User Two Factor Method Remove
      • User Update
      • User Update Complete
  • Example Apps
    • Overview
    • Dart
    • Go
    • Java
    • JavaScript
    • .NET Core
    • PHP
    • Python
    • Ruby
  • Lambdas
    • Overview
    • Apple Reconcile
    • Client Cred. JWT Populate
    • Epic Games Reconcile
    • External JWT Reconcile
    • Facebook Reconcile
    • Google Reconcile
    • HYPR Reconcile
    • JWT Populate
    • LDAP Connector Reconcile
    • LinkedIn Reconcile
    • Nintendo Reconcile
    • OpenID Connect Reconcile
    • SAML v2 Populate
    • SAML v2 Reconcile
    • SCIM Group Req. Converter
    • SCIM Group Resp. Converter
    • SCIM User Req. Converter
    • SCIM User Resp. Converter
    • Sony PSN Reconcile
    • Steam Reconcile
    • Twitch Reconcile
    • Twitter Reconcile
    • Xbox Reconcile
  • Identity Providers
    • Overview
    • Apple
    • Epic Games
    • External JWT
      • Overview
      • Example
    • Facebook
    • Google
    • HYPR
    • LinkedIn
    • Nintendo
    • OpenID Connect
      • Overview
      • Azure AD
      • Discord
      • Github
    • Sony PlayStation Network
    • Steam
    • Twitch
    • Twitter
    • SAML v2
      • Overview
      • ADFS
    • SAML v2 IdP Initiated
      • Overview
      • Okta
    • Xbox
  • Messengers
    • Overview
    • Generic Messenger
    • Kafka Messenger
    • Twilio Messenger
  • Connectors
    • Overview
    • Generic Connector
    • LDAP Connector
    • FusionAuth Connector
  • Self Service Account Mgmt
    • Overview
    • Updating User Data & Password
    • Add Two-Factor Authenticator
    • Add Two-Factor Email
    • Add Two-Factor SMS
    • Customizing
    • Troubleshooting
  • Advanced Threat Detection
    • Overview
  • Integrations
    • Overview
    • CleanSpeak
    • Kafka
    • Twilio
  • OpenID Connect & OAuth 2.0
    • Overview
    • Endpoints
    • Tokens
  • SAML v2 IdP
    • Overview
    • Google
    • Zendesk
  • Plugins
    • Plugins
    • Writing a Plugin
    • Custom Password Hashing
  • Guides
    • Overview
    • Advanced Registration Forms
    • Breached Password Detection
    • Multi-Factor Authentication
    • Multi-Tenant
    • Passwordless
    • Securing Your APIs
    • Silent Mode
    • Single Sign-on
  • Tutorials
    • Overview
    • User Control & Gating
      • Gate Unverified Users
      • Gate Unverified Registrations
      • User Account Lockout
    • Setup Wizard & First Login
    • Register/Login a User
    • Start and Stop FusionAuth
    • Authentication Tokens
    • Key Rotation
    • JSON Web Tokens
    • Prometheus Setup
    • Switch Search Engines
    • Two Factor (pre 1.26)
  • Reference
    • CORS
    • Configuration
    • Data Types
    • Known Limitations
    • Password Hashes

    Migration Tutorial

    Overview

    This tutorial shows you how to migrate user data from a single existing user database into FusionAuth.

    In addition to the example code provided here, you may find example code relevant to your migration in our Import Scripts GitHub repository.

    You also may be interested in the general migration guide which covers the topic in more depth.

    In many cases, you’ll have an existing user database in MySQL, Mongo, or another similar database. In many cases, your user table (or objects) will contain the user information that your application needs in columns or properties. Here’s an example table structure for a relational database for a user:

    CREATE TABLE user (
      id INTEGER NOT NULL AUTO_INCREMENT,
      name VARCHAR(255) NULL,
      email VARCHAR(255) NOT NULL,
      password VARCHAR(255) NOT NULL,
      profile_picture_url VARCHAR(255) NOT NULL,
      profile_description TEXT,
      role VARCHAR(255) NOT NULL,
      ...
    );

    This data will be migrated into FusionAuth by exporting it from the existing database and then importing it into FusionAuth.

    Password Encryption

    The first step of the migration process is to determine how passwords are hashed in your current user database. If they are not hashed, you can skip this step and FusionAuth will automatically hash them for you during the import process. Once you have determined the hashing algorithm used in your existing database, you will need to write a password hashing plugin. The documentation for writing plugins and a custom password hasher are located here:

    • Plugins

    • Custom Password Hashing

    Create the Applications

    Next, you will need to create all of the Applications in FusionAuth that users will be registered with. For example, you might have a website and a forum that are both using the same user database. In this case, you will need to create a FusionAuth Application for your website and another Application for your forum.

    Once you have created the Applications, store the IDs for each so that you can use them during the import process.

    For our example above, we will assume only a single Application called Website with a UUID of 79a34811-d627-4751-bb9c-9ab148ab8dc9.

    Determine FusionAuth Data Locations

    FusionAuth has a number of properties on the base User object. You can read about those properties in the Create a User API section. Your existing database might have additional user properties that you need to migrate. These can be stored in the data object inside the User object. This object is also described in Create a User API section. The data object allows completely free-form data to be stored.

    Additionally, each user can have 0 or more registrations created during the import. Registrations are used to control access to your application(s) and also provide authorization via roles for each application. Registrations can also have a data object to store additional attributes for each user. You will need to determine if you want to store your additional user data on the base User object or the Registration object. The choice might depend on if the data is used globally for all of your applications or just in a single application.

    For our example above, we’ll place all of our extra data in a Registration object for our Website Application.

    Export/Import the Existing User Data

    The simplest way to migrate the data from an existing database to FusionAuth is to write a program or script that reads records from the existing database and batch imports them into FusionAuth. We won’t write a complete script here, but here is some pseudo code you can use when building your script:

    Migration Script Example
    def existingUser
    def importUsers = []
    
    while ((existingUser = readNextUser()) != null) {
      def fusionauthUser = {
        fullName: existingUser.name,
        email: existingUser.email,
        password: existingUser.password,
        encryptionScheme: "my-custom-encryption-scheme",
        imageURL: existingUser.profilePicture,
        registrations: [
          {
            applicationID: "79a34811-d627-4751-bb9c-9ab148ab8dc9",
            data: {
              profileDescription: existingUser.profileDescription
            }
            roles: [
              existingUser.role
            ]
          }
        ]
      }
    
      importUsers.add(fusionauthUser)
    }
    
    FusionAuthClient client = new FusionAuthClient("http://localhost:9011", "my-api-key")
    client.importUsers(new ImportRequest(importUsers))

    This code reads each user from the existing database, creates a new FusionAuth User object from the existing user data, and then bulk imports all of the users into FusionAuth in one request. Generally speaking this process works for small databases (under 10,000 users). If you have a large database, you will want to import users in blocks of 1,000 or 10,000 to avoid crashing FusionAuth.

    This example uses a FusionAuthClient to perform the import. You may also call the Import Users API directly if you prefer (or if a FusionAuthClient is not available for your language of choice).

    Feedback

    How helpful was this page?

    See a problem?

    File an issue in our docs repo

    © 2021 FusionAuth
    Subscribe for developer updates