> For the complete MongoDB documentation index, see www.mongodb.com/docs/llms.txt

# Create an Encryption Schema

## About this Task

To make encrypted fields queryable, create an [encryption schema](https://www.mongodb.com/docs/manual/reference/glossary.md#std-term-encryption-schema). This schema defines which fields are queryable, and which query types are permitted. For more information, see [Encrypted Fields and Enabled Queries.](https://www.mongodb.com/docs/manual/core/queryable-encryption/fundamentals/encrypt-and-query.md#std-label-qe-fundamentals-encrypt-query)

**Important:**

Queryable Encryption supports equality, range, prefix, suffix, and substring queries. You can configure a field for only one of the equality or range query types. You can enable both `prefix` and `suffix` on the same field, but you can't combine `substring` with another query type.

## Before you Begin

When you make encrypted fields queryable, consider performance and security. For details on how each configuration option affects these, see [Configure Encrypted Fields for Optimal Search and Storage.](https://www.mongodb.com/docs/manual/core/queryable-encryption/fundamentals/encrypt-and-query.md#std-label-qe-field-configuration)

To estimate the storage that prefix, suffix, and substring queries require before you configure them, see [Estimate Queryable Encryption Storage Impact.](https://www.mongodb.com/docs/manual/core/queryable-encryption/qe-estimate-storage-impact.md#std-label-qe-estimate-storage-impact)

## Field Reference

You can configure encryption for each field in the `fields` array of your `encryptedFieldsObject`. The following table describes the available subfields:

| Field | Type | Description |
| --- | --- | --- |
| `path` | String | **Required.** The dot-notation path to the field to encrypt, such as `"patientInfo.ssn"`. You can specify any field except the `_id` field. |
| `bsonType` | String | **Required.** The [BSON type](https://www.mongodb.com/docs/manual/reference/bson-types.md#std-label-bson-types) of the field to encrypt. For a complete list of supported types, see [BSON Types.](https://www.mongodb.com/docs/manual/core/queryable-encryption/reference/supported-operations.md#std-label-qe-commands-supported-bson-types) |
| `keyId` | UUID | *Optional.* The UUID of the DEK (Data Encryption Key) to use for encrypting this field. The UUID is a BSON [binary data](http://bsonspec.org/spec.html) element of subtype `4`. Key IDs must be unique. Specifying a `keyId` that is already in use returns an error. If omitted, you can use the `createEncryptedCollection()` helper method to create keys automatically. |
| `queries` | Object | *Optional.* Enables querying on this encrypted field. If omitted, the field is encrypted but not queryable. To learn more about query options, see [Configure Encrypted Fields for Optimal Search and Storage.](https://www.mongodb.com/docs/manual/core/queryable-encryption/fundamentals/encrypt-and-query.md#std-label-qe-field-configuration) |

## Steps

1. Create the encryption schema.

   Include an `encryptedFieldsObject` with a nested `fields` array:

   ```javascript
   const encryptedFieldsObject = {
      fields: []
   }
   ```

2. Specify fields to encrypt.

   Add the `path` and `bsonType` strings to a document within the fields array:

   ```javascript
   const encryptedFieldsObject = {
      fields: [
         {
            path: "myDocumentField",
            bsonType: "int"
         }
      ]
   }
   ```

   **Important:**

   You can specify any field for encryption except the `_id` field.

   Optionally, set a `keyId` field with the DEK (Data Encryption Key) ID.

   **Important:**

   Key IDs must be unique, otherwise the server returns an error.

   By configuring `AutoEncryptionSettings` on the client, you can use the `createEncryptedCollection` helper method to create keys automatically.

   ```javascript
   {
      path: "myDocumentField",
      bsonType: "int",
      keyId: "<unique data encryption key>"
   }
   ```

3. Enable equality queries on desired fields.

   This enables querying with the [`$eq`](https://www.mongodb.com/docs/manual/reference/operator/query/eq.md#mongodb-query-op.-eq), [`$ne`](https://www.mongodb.com/docs/manual/reference/operator/query/ne.md#mongodb-query-op.-ne), [`$in`](https://www.mongodb.com/docs/manual/reference/operator/query/in.md#mongodb-query-op.-in), and [`$nin`](https://www.mongodb.com/docs/manual/reference/operator/query/nin.md#mongodb-query-op.-nin) operators.

   Add the `queries` object and set `queryType` to `"equality"`:

   ```javascript
   {
      path: "myDocumentField",
      bsonType: "int",
      queries: { queryType: "equality" }
   }
   ```

4. Enable range queries on desired fields.

   This enables querying with the [`$lt`](https://www.mongodb.com/docs/manual/reference/operator/query/lt.md#mongodb-query-op.-lt), [`$lte`](https://www.mongodb.com/docs/manual/reference/operator/query/lte.md#mongodb-query-op.-lte), [`$gt`](https://www.mongodb.com/docs/manual/reference/operator/query/gt.md#mongodb-query-op.-gt), and [`$gte`](https://www.mongodb.com/docs/manual/reference/operator/query/gte.md#mongodb-query-op.-gte) operators.

   For details on how the following options affect security and performance, see [Configure Encrypted Fields for Optimal Search and Storage.](https://www.mongodb.com/docs/manual/core/queryable-encryption/fundamentals/encrypt-and-query.md#std-label-qe-field-configuration)

   Add the `queries` object and set `queryType` to `"range"`:

   ```javascript
   {
      path: "myDocumentRangeField",
      bsonType: "int",
      queries: { queryType: "range" }
   }
   ```

   Set the following fields:

   | Field | Type | Description |
   | --- | --- | --- |
   | [min and max](https://www.mongodb.com/docs/manual/core/queryable-encryption/fundamentals/encrypt-and-query.md#std-label-qe-field-min-max) | Same as field `bsonType` | Required if `bsonType` is `decimal` or `double`. Optional but highly recommended if it is `int`, `long`, or `date`. Defaults to the minimum and maximum values of the `bsonType`. When possible, specifying bounds on a query improves performance. If querying values outside of these inclusive bounds, MongoDB returns an error. |

   ```javascript
   {
      path: "myDocumentRangeField",
      bsonType: "int",
      queries: { queryType: "range",
                 min: 0,
                 max: 1200
      }
   }
   ```

5. Enable prefix, suffix, or substring queries on desired fields.

   These query types are for `string` fields only. You can enable both `prefix` and `suffix` on the same field, but can't enable either if using `substring`.

   - `prefix` queries enable the [`$encStrStartsWith`](https://www.mongodb.com/docs/manual/reference/operator/aggregation/encstrstartswith.md#mongodb-expression-exp.-encStrStartsWith) and [`$encStrNormalizedEq`](https://www.mongodb.com/docs/manual/reference/operator/aggregation/encstrnormalizedeq.md#mongodb-expression-exp.-encStrNormalizedEq) aggregation expressions.

   - `suffix` queries enable the [`$encStrEndsWith`](https://www.mongodb.com/docs/manual/reference/operator/aggregation/encstrendswith.md#mongodb-expression-exp.-encStrEndsWith) and [`$encStrNormalizedEq`](https://www.mongodb.com/docs/manual/reference/operator/aggregation/encstrnormalizedeq.md#mongodb-expression-exp.-encStrNormalizedEq) aggregation expressions.

   - `substring` queries enable the [`$encStrContains`](https://www.mongodb.com/docs/manual/reference/operator/aggregation/encstrcontains.md#mongodb-expression-exp.-encStrContains) and [`$encStrNormalizedEq`](https://www.mongodb.com/docs/manual/reference/operator/aggregation/encstrnormalizedeq.md#mongodb-expression-exp.-encStrNormalizedEq) aggregation expressions.

   Add the `queries` object and set `queryType` to `"prefix"`, `"suffix"`, or `"substring"`:

   ```javascript
   {
      path: "myDocumentStringField",
      bsonType: "string",
      queries: { queryType: "substring" }
   }
   ```

   Set the following fields.

   For details on how they affect security and performance, see [Configure Encrypted Fields for Optimal Search and Storage.](https://www.mongodb.com/docs/manual/core/queryable-encryption/fundamentals/encrypt-and-query.md#std-label-qe-field-configuration)

   | Field | Type | Description |
   | --- | --- | --- |
   | [`strMaxLength`](https://www.mongodb.com/docs/manual/core/queryable-encryption/fundamentals/encrypt-and-query.md#mongodb-parameter-param.strMaxLength) | integer | `substring` queries only. The maximum allowed length for a substring-indexed field. |
   | [`strMinQueryLength`](https://www.mongodb.com/docs/manual/core/queryable-encryption/fundamentals/encrypt-and-query.md#mongodb-parameter-param.strMinQueryLength) | integer | The minimum allowed prefix/suffix/substring length to query. |
   | [`strMaxQueryLength`](https://www.mongodb.com/docs/manual/core/queryable-encryption/fundamentals/encrypt-and-query.md#mongodb-parameter-param.strMaxQueryLength) | integer | The maximum allowed prefix/suffix/substring length to query. IMPORTANT: This setting strongly impacts query performance. Limit it whenever possible. |
   | [`caseSensitive`](https://www.mongodb.com/docs/manual/core/queryable-encryption/fundamentals/encrypt-and-query.md#mongodb-parameter-param.caseSensitive) | Boolean | Optional. Whether queries are case-sensitive. Defaults to `true`. |
   | [`diacriticSensitive`](https://www.mongodb.com/docs/manual/core/queryable-encryption/fundamentals/encrypt-and-query.md#mongodb-parameter-param.diacriticSensitive) | Boolean | Optional. Whether queries are diacritic-sensitive. Defaults to `true`. |

   ```javascript
   {
      path: "myDocumentStringField",
      bsonType: "string",
      queries: {
         "queryType": "substring",
         "strMaxLength": 30,
         "strMinQueryLength": 1,
         "strMaxQueryLength": 20,
         "caseSensitive": false
      }
   }
   ```

## Example

This example shows how to create an encryption schema for hospital data.

Consider the following document that contains personally identifiable information (PII), credit card information, and sensitive medical information:

```json
{
   "firstName": "Jon",
   "lastName": "Snow",
   "patientId": 12345187,
   "address": "123 Cherry Ave",
   "medications": [
      "Adderall",
      "Lipitor"
   ],
   "patientInfo": {
      "ssn": "921-12-1234",
      "billing": {
            "type": "visa",
            "number": "1234-1234-1234-1234"
      }
   }
}
```

To ensure the PII and sensitive medical information stays secure, this encryption schema adds the relevant fields:

```javascript
const encryptedFieldsObject = {
   fields: [
      {
         path: "patientId",
         bsonType: "int"
      },
      {
         path: "patientInfo.ssn",
         bsonType: "string"
      },
      {
         path: "medications",
         bsonType: "array"
      },
      {
         path: "patientInfo.billing",
         bsonType: "object"
      }
   ]
}
```

Adding the `queries` property makes the `patientId` and `patientInfo.ssn` fields queryable. This example enables equality queries:

```javascript
const encryptedFieldsObject = {
   fields: [
      {
         path: "patientId",
         bsonType: "int",
         queries: { queryType: "equality" }
      },
      {
         path: "patientInfo.ssn",
         bsonType: "string",
         queries: { queryType: "equality" }
      },
      {
         path: "medications",
         bsonType: "array"
      },
      {
         path: "patientInfo.billing",
         bsonType: "object"
      },
   ]
}
```
