> For the complete documentation index, see [llms.txt](https://user.netmera.com/netmera-developer-guide/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://user.netmera.com/netmera-developer-guide/api-documentation/recipes/creating-and-managing-segments.md).

# Creating and Managing Segments

Create a segment from a profile attribute or a group of conditions, follow its calculation, update it, delete or reopen it, and send an email to it.

This recipe shows how to manage the lifecycle of a segment through the REST API: create it from a profile attribute condition or from a group of conditions, wait for the calculation to finish, change the condition, delete the segment when it is no longer needed, and reopen it when it is needed again. It also shows how to send an email to the segment, and which requests are rejected before a campaign is created. Segments created this way appear in the Netmera panel, and their Targeting Rules are filled from the request.

## When to Use

This recipe fits integrations that keep Netmera audiences in line with rules owned by an external system, such as a CRM or a data platform that decides who belongs to an audience.

## Prerequisites

* REST API key of the application
* The code of every profile attribute used in a condition, for example `email`
* Enough room in the segment limit of the application package
* For the email scenario: the Template ID of an email template created in the panel

## How Segment Services Behave

Four rules apply to every call in this recipe.

* **The name must be unique.** A segment with a name that already exists returns error code 5025.
* **A condition is required.** A request without any condition is rejected as an invalid parameter ("Empty criteria"). Exceeding the segment limit of the application package returns a quota error.
* **The calculation is asynchronous.** A new or updated segment is saved with `segmentStatus` `WAITING_CALCULATE` and becomes `READY` when the calculation finishes. Wait for `READY` before sending to the segment, and follow the status with `getSegment`.
* **The server sets some fields.** `createdBy` is always `REST`. The status, the user count, the segment type, and the business unit are not read from the request. The REST API creates standard (condition-based) segments only.

Relative dates in behavior conditions, such as "today" or "last 7 days", use the `timeZone` value in IANA format, for example `Europe/Istanbul`. When it is not sent, the time zone of the application is used.

## Step 1: Create a Segment from a Profile Attribute

Send the name of the segment in `segment.segmentName` and a single profile attribute condition in `profile`. This example creates a segment of the users whose email address contains `example`.

```bash
curl https://restapi.netmera.com/rest/3.0/createSegment \
  --request POST \
  --header 'Accept: */*' \
  --header 'Content-Type: application/json' \
  --header 'X-netmera-api-key: <API_KEY>' \
  --data '{
  "segment": {
    "segmentName": "Email contains example"
  },
  "profile": {
    "type": "PROFILE",
    "expression": {
      "code": "email",
      "operator": "CONTAINS",
      "values": ["example"]
    }
  }
}'
```

The response returns the segment in the waiting state:

```json
{
  "segmentStatus": "WAITING_CALCULATE",
  "userCount": null,
  "createdBy": "REST",
  "name": "Email contains example",
  "id": 5,
  "status": "ACTIVE"
}
```

**Expected result:** A segment with an `id`, `segmentStatus` set to `WAITING_CALCULATE`, and `userCount` set to `null`. Keep the `id` for the next steps.

## Step 2: Create a Segment from a Group of Conditions

Use `targetJson` when a segment needs more than one condition. A group has a `type` of `GROUP`, a `logic` that joins its conditions, and a list of `conditions`. This example combines a channel permission with a profile attribute: the segment contains the users who have email permission and whose email address contains `example`.

```bash
curl https://restapi.netmera.com/rest/3.0/createSegment \
  --request POST \
  --header 'Accept: */*' \
  --header 'Content-Type: application/json' \
  --header 'X-netmera-api-key: <API_KEY>' \
  --data '{
  "segment": {
    "segmentName": "Email opt-in and email contains example"
  },
  "targetJson": {
    "id": "group_1",
    "type": "GROUP",
    "logic": "AND",
    "conditions": [
      {
        "type": "CHANNEL",
        "operator": "EQUALS",
        "value": "EMAIL",
        "logic": "AND"
      },
      {
        "type": "PROFILE",
        "operator": "EQUALS",
        "value": "email",
        "expression": {
          "code": "email",
          "operator": "CONTAINS",
          "values": ["example"]
        },
        "logic": "AND"
      }
    ]
  }
}'
```

The response has the same shape as in Step 1, with the name and the `id` of the new segment.

**Expected result:** A second segment in the `WAITING_CALCULATE` state. In the panel, the Targeting Rules of the segment show the channel and profile conditions of the request.

## Step 3: Follow the Calculation

Read the segment with `getSegment` and the `id` returned in Step 1. Repeat the call until `segmentStatus` is `READY`.

```bash
curl 'https://restapi.netmera.com/rest/3.0/getSegment?id=5' \
  --header 'Accept: */*' \
  --header 'X-netmera-api-key: <API_KEY>'
```

```json
{
  "segmentStatus": "READY",
  "userCount": 20,
  "createdBy": "REST",
  "name": "Email contains example",
  "id": 5,
  "status": "ACTIVE"
}
```

**Expected result:** `segmentStatus` is `READY` and `userCount` holds the number of users in the segment. The segment can now be used as a target.

## Step 4: Update a Segment

`updateSegment` takes the same request as `createSegment`, with the ID of the segment in `segment.segmentId`. This example changes the condition of the segment from Step 1.

```bash
curl https://restapi.netmera.com/rest/3.0/updateSegment \
  --request POST \
  --header 'Accept: */*' \
  --header 'Content-Type: application/json' \
  --header 'X-netmera-api-key: <API_KEY>' \
  --data '{
  "segment": {
    "segmentId": 5,
    "segmentName": "Email contains example"
  },
  "profile": {
    "type": "PROFILE",
    "expression": {
      "code": "email",
      "operator": "CONTAINS",
      "values": ["example.com"]
    }
  }
}'
```

The segment is calculated again after the update, so the response shows `WAITING_CALCULATE` and a `userCount` of `null`. The Targeting Rules of the segment in the panel are updated to match the request.

```json
{
  "segmentStatus": "WAITING_CALCULATE",
  "userCount": null,
  "createdBy": null,
  "name": "Email contains example",
  "id": 5,
  "status": "ACTIVE"
}
```

The calculation is asynchronous. Wait for a while, and then read the segment with `getSegment` as in Step 3 to see the new result.

**Expected result:** After the recalculation, `getSegment` returns `READY` with the user count of the new condition.

## Step 5: Delete a Segment

Delete a segment with `changeSegmentStatus`. Pass the `id` of the segment and `DELETED` as the `status` in the query string. The request has no body. A segment that an active campaign uses cannot be deleted.

```bash
curl 'https://restapi.netmera.com/rest/3.0/changeSegmentStatus?id=5&status=DELETED' \
  --request POST \
  --header 'Accept: */*' \
  --header 'X-netmera-api-key: <API_KEY>'
```

```json
{
  "segmentStatus": "WAITING_DELETED",
  "userCount": 72,
  "createdBy": "REST",
  "name": "Email contains example",
  "id": 5,
  "status": "DELETED"
}
```

**Expected result:** The response shows `status` set to `DELETED` and `segmentStatus` set to `WAITING_DELETED`.

## Step 6: Reopen a Deleted Segment

A deleted segment comes back with the same service. Pass `ACTIVE` as the `status`.

```bash
curl 'https://restapi.netmera.com/rest/3.0/changeSegmentStatus?id=5&status=ACTIVE' \
  --request POST \
  --header 'Accept: */*' \
  --header 'X-netmera-api-key: <API_KEY>'
```

A reopened segment counts against the segment limit of the application package again, and it is calculated again. Read it with `getSegment` as in Step 3 until `segmentStatus` is `READY`.

**Expected result:** The segment has `status` set to `ACTIVE`, and after the calculation `segmentStatus` is `READY`. Until then, a send request that names the segment can be rejected, as described in the last scenario below.

## More Scenarios

### Combine a Tag and a Profile Condition

Send a tag condition in `tags` and a profile condition in `profile`. The `<type>ConditionType` field in `segment` decides how that condition joins the ones before it. In this example, the segment contains the users who carry a tag and whose email address contains `example`. `<TAG_ID>` is the ID of the tag, and `timeZone` is optional.

```bash
curl https://restapi.netmera.com/rest/3.0/createSegment \
  --request POST \
  --header 'Accept: */*' \
  --header 'Content-Type: application/json' \
  --header 'X-netmera-api-key: <API_KEY>' \
  --data '{
  "segment": {
    "segmentName": "Newsletter subscribers",
    "profileConditionType": "AND"
  },
  "tags": {
    "type": "TAG",
    "logic": "AND",
    "code": "<TAG_ID>"
  },
  "profile": {
    "type": "PROFILE",
    "logic": "AND",
    "expression": {
      "code": "email",
      "operator": "CONTAINS",
      "values": ["example"]
    }
  },
  "timeZone": "Europe/Istanbul"
}'
```

**Expected result:** A segment in the `WAITING_CALCULATE` state, as in Step 1.

### Send an Email to a Segment

When `getSegment` returns `READY`, name the segment in `target.segment` of `sendBulkEmail`. `target` takes only one of `segment`, `tag`, or `sendToAll`.

```bash
curl https://restapi.netmera.com/rest/3.0/sendBulkEmail \
  --request POST \
  --header 'Accept: */*' \
  --header 'Content-Type: application/json' \
  --header 'X-netmera-api-key: <API_KEY>' \
  --data '{
  "emailTemplateId": <TEMPLATE_ID>,
  "subject": "Daily Bulletin",
  "emailIysMessageType": "C",
  "customParams": {
    "TITLE": "Market Summary"
  },
  "target": {
    "segment": "Email contains example"
  }
}'
```

`emailIysMessageType` selects the recipients. `C`, or leaving the field out, sends only to the users who have email permission. `N` sends to every user who has an email address and is not in the suppression list or the blacklist. Every link in the template, and in the HTML that arrives through `customParams`, gets an `nm_campid` parameter, so the clicks appear in the campaign report.

**Expected result:** The request is accepted with HTTP 200 and returns the `notificationKey` of the campaign. The target count in the campaign report is greater than 0.

### Requests That Are Rejected

`sendBulkEmail` and `sendBulkNotification` check the target segment before they create a campaign. A rejected request returns HTTP 400, and no campaign is created.

| Segment state                                                                  | Result                                                                                        |
| ------------------------------------------------------------------------------ | --------------------------------------------------------------------------------------------- |
| `ACTIVE` and `READY`                                                           | Accepted                                                                                      |
| `ACTIVE`, `WAITING_CALCULATE`, and calculated before (`userCount` has a value) | Accepted. The earlier user list is used while the segment is calculated again.                |
| `ACTIVE`, `WAITING_CALCULATE`, and never calculated                            | Rejected: `Segment '<name>' is still being calculated; retry when its segmentStatus is READY` |
| `DELETED`, `WAITING_DELETED`, or no segment with that name                     | Rejected: `Segment '<name>' is not active`                                                    |

When `target.segment` is a list, the request is rejected if one segment of the list fails the check. To see the first rejection, call `sendBulkEmail` right after `createSegment`, with the name of the new segment:

```bash
curl https://restapi.netmera.com/rest/3.0/sendBulkEmail \
  --request POST \
  --header 'Accept: */*' \
  --header 'Content-Type: application/json' \
  --header 'X-netmera-api-key: <API_KEY>' \
  --data '{
  "emailTemplateId": <TEMPLATE_ID>,
  "subject": "Test",
  "customParams": {
    "TITLE": "Test"
  },
  "target": {
    "segment": "<NEW_SEGMENT_NAME>"
  }
}'
```

The same request with the name of a deleted segment returns the second rejection. `sendBulkEmail` also rejects these requests before it saves the email:

* The subject contains an HTML tag or a line break.
* The HTML of the template is empty.
* A forbidden word set in the application settings of the panel appears in the email. The check covers the values in `customParams` too.
* The send time is outside the email time restriction of the application.

A `createSegment` request with the name of an existing segment is rejected with error code 5025.

**Expected result:** Each request returns HTTP 400, the email is not sent, and no campaign draft is created.

## Verification Checklist

* The segment name is unique in the application
* The request carries a condition in either `profile` or `targetJson`
* `getSegment` returns `segmentStatus` `READY` before the segment is used as a target
* A deleted segment is reopened, and `READY` again, before a send request names it
* After an update, the segment is read again, because the calculation starts over
* The segment appears in the panel with the Targeting Rules of the request
* `changeSegmentStatus` is called with the `id` of the correct segment, because the request carries no other confirmation
* `target` of `sendBulkEmail` holds only one of `segment`, `tag`, or `sendToAll`

## Related Pages

To read the segments of the application and their members, see [Reading Segments and Segment Members](/netmera-developer-guide/api-documentation/recipes/reading-segments-and-members.md). To send a push to a segment, see [Targeting a Push Campaign by Segment or Profile Attribute](/netmera-developer-guide/api-documentation/recipes/targeting-by-segment-or-profile.md). To send a different HTML body to a segment in every send, see [Sending Bulk Email with Dynamic HTML Content](/netmera-developer-guide/api-documentation/recipes/sending-bulk-email-with-dynamic-html.md). The full format of each endpoint is in the Segment Management section of the [User & Device Management](/netmera-developer-guide/api-documentation/rest-api/user-and-device-management.md#segment-management) page.


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation by asking a question.

Perform an HTTP GET request on the following URL with the `ask` and `goal` query parameters:

```
GET https://user.netmera.com/netmera-developer-guide/api-documentation/recipes/creating-and-managing-segments.md?ask=<question>&goal=<user_goal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is what the user is ultimately trying to achieve, the reason they need the answer. Sharing it helps GitBook give you a better, more relevant answer. A goal is most helpful when it describes the outcome the user wants rather than restating the question. For example, with `ask=how do I create an API token`, a goal like `automate deployments from our CI pipeline` lets GitBook tailor the answer to that use case.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
