Understanding Virtual Fields in Phoenix Schemas: A Comprehensive Guide

·

4 min read

Understanding Virtual Fields in Phoenix Schemas: A Comprehensive Guide

When working with Phoenix, the web framework built on Elixir, you’ll often find yourself defining schemas to map your database tables to Elixir structs. These schemas are powerful tools that help manage data interactions in a clean, structured way. But sometimes, you may need to work with fields that aren't stored in the database—this is where virtual fields come in.

In this article, we’ll explore what virtual fields are, why they are useful, and how to implement them in your Phoenix schemas.

What Are Virtual Fields?

A virtual field is a field that is part of your schema but is not persisted in your database. Unlike regular fields, virtual fields exist purely in the context of your application, often used for temporary data or operations that don’t require the field to be stored.

For example, you might use a virtual field to handle password confirmation during user registration or to store a derived value that doesn’t need to be saved.

Why Use Virtual Fields?

Virtual fields can be incredibly useful in various scenarios:

  1. Temporary Data Storage: Sometimes, you need to store data temporarily during an operation, such as when validating form inputs or handling file uploads.

  2. Derived Values: If you need to calculate a value based on other fields, a virtual field can be a good place to store this derived value without polluting your database.

  3. Enhanced Security: For fields like password confirmations or tokens that should not be stored, virtual fields ensure that sensitive information isn’t accidentally saved in your database.

  4. Clean Code: Using virtual fields keeps your code clean and easy to maintain, as you don’t need to create additional columns in your database for temporary or calculated data.

How to Define Virtual Fields in Phoenix

Defining a virtual field in a Phoenix schema is straightforward. You can define it just like any other field, but with the virtual: true option.

Here’s an example:

defmodule MyApp.Accounts.User do
  use Ecto.Schema

  schema "users" do
    field :email, :string
    field :password_hash, :string
    field :password, :string, virtual: true
    field :password_confirmation, :string, virtual: true

    timestamps()
  end
end

In this example, password and password_confirmation are virtual fields. They will not be stored in the users table in the database but can be used in your application logic.

Using Virtual Fields in Changesets

Virtual fields are often used in changesets for validation and transformations. Here’s how you might validate a user’s password and confirmation:

defmodule MyApp.Accounts.User do
  use Ecto.Schema
  import Ecto.Changeset

  schema "users" do
    field :email, :string
    field :password_hash, :string
    field :password, :string, virtual: true
    field :password_confirmation, :string, virtual: true

    timestamps()
  end

  def changeset(user, attrs) do
    user
    |> cast(attrs, [:email, :password, :password_confirmation])
    |> validate_required([:email, :password, :password_confirmation])
    |> validate_length(:password, min: 6)
    |> validate_confirmation(:password)
    |> hash_password()
  end

  defp hash_password(changeset) do
    if password = get_change(changeset, :password) do
      put_change(changeset, :password_hash, Bcrypt.hash_pwd_salt(password))
    else
      changeset
    end
  end
end

In this changeset, password and password_confirmation are cast from the input parameters, validated, and used to generate a password_hash that is stored in the database. The virtual fields allow you to work with these values without persisting them.

Common Use Cases for Virtual Fields

  1. Password Handling: As shown in the example above, virtual fields are often used to handle passwords securely by ensuring that plain text passwords are not stored in the database.

  2. Token Management: Virtual fields can be used for managing temporary tokens, such as email verification tokens or password reset tokens.

  3. Form Input Processing: When processing multi-step forms, virtual fields can temporarily store user inputs that are not yet ready to be saved in the database.

  4. Computed Fields: For example, you might have a full_name virtual field that combines first_name and last_name fields.

Conclusion

Virtual fields in Phoenix schemas provide a powerful and flexible way to manage data that doesn’t need to be stored in your database. By using virtual fields, you can keep your schema clean, enhance security, and handle complex operations without unnecessary database changes.

Understanding when and how to use virtual fields will make your Phoenix applications more robust and easier to maintain. Whether you're handling sensitive data like passwords or working with derived values, virtual fields are an essential tool in your Phoenix development toolkit.


At ElixirMasters, we specialize in creating robust and scalable web applications using Phoenix and Elixir. If you're looking to build real-time applications, optimize your existing infrastructure, or integrate Elixir into your tech stack, we are here to help.

For more information about how we can assist your business with Elixir development, visit ElixirMasters or get in touch with us today. Our parent company, BetaMize, also offers a wide range of digital transformation services for businesses looking to leverage modern technology for growth.

Let’s build something great together!