---
updatedAt: 2025-12-15T13:13:36.000Z
agentTools:
  projectIndex: https://cloud.docs.tamr.com/llms.txt
---

# Linking Your Data Using the Relationships API

The Relationships API helps you create a web of linked information that mirrors real-world connections within your data. For instance, you might link members of a household, healthcare providers and organizations, or subsidiary companies and their headquarters.

This topic provides Python examples to call the API and establish parent-child relationships between company records.

# Viewing Available Relationship Types

First, check which relationship types have already been configured on your tenant using a GET request to [list relationship types](https://cloud.docs.tamr.com/tamr-cloud/reference/relationships_listrelationshiptypes).

If you need to set up new relationship types, please contact <help@tamr.com.>

1. Import the `requests` library in Python to help call the API.
2. Construct the URL, making sure to provide your specific`<tenant-name>` and the `tableId` for your data.  The `tableId` is available on the data product's Manage System of Record page (see [Configuring a Data Product for Tamr RealTime](https://cloud.docs.tamr.com/tamr-cloud/docs/configuring-a-data-product-for-tamr-realtime)).
3. Set the headers, including your `X-API-KEY` for authentication.

```python
import requests

url = "https\://<tenant-name>.tamr.cloud/api/v1alpha1/relationships/types:list?tableId=`tbl_<id>"

headers = {  
    "accept": "application/json",  
    "X-API-KEY": "example-api-key"  
}

response = requests.get(url, headers=headers)  
print(response.text)
```

The API response includes all configured relationship types.

The example below shows one relationship type for linking a child company to its parent, with the relationship defined by the `forwardName` ("is child of") and `reverseName` ("is parent of").

```python
{
    "relationshipTypes": [
        {
            "relationshipTypeId": "reltyp_<id>",
            "versionId": "32969596",
            "forwardName": "is child of",
            "reverseName": "is parent of",
            "description": "Represents a child/parent relationship between companies.",
            "createTime": "2025-09-23T16:33:39.118Z",
            "updateTime": "2025-09-25T19:54:19.452Z"
        }
    ]
}
```

# Creating New Relationships

You can create new relationships by:

* Using the API to link two records
* Automating relationship creation
* Uploading relationships in bulk using a workflow

## Linking Two Records

Once you know the `relationshipTypeId`, you  can make a `POST` request to [create](https://cloud.docs.tamr.com/tamr-cloud/reference/relationships_createrelationship) new relationships between records in the same table or between different tables.

This example demonstrates how to create relationships between a child and parent company in the same table.

1. Define the URL for the relationships endpoint.
2. Create the `payload`, which specifies the link you want to create. You need:
   * `fromTableId` and `fromRecordId`: The source record of the relationship (child record).
   * `toTableId` and `toRecordId`: The destination record of the relationship (parent record).
   * `relationshipTypeId`: The ID for the type of relationship you're creating, which you found in the previous step.
3. Set the headers, including your `X-API-KEY` and the `content-type`.

```python
import requests

url = "https://<tenant-name>.tamr.cloud/api/v1alpha1/relationships"

payload = {
    "fromTableId": "tbl_<id_1>",
    "fromRecordId": "rec_<id_a>",
    "toTableId": "tbl_<id_1>",
    "toRecordId": "rec_<id_b>",
    "relationshipTypeId": "reltyp_<id>"
}

headers = {
    "accept": "application/json",
    "X-API-KEY": "example-api-key",
    "content-type": "application/json"
}

response = requests.post(url, json=payload, headers=headers)
print(response.text)

```

A successful request returns a response confirming the details of the relationship that was just created.

```python
{
  "relationship": {
    "relationshipId": "rel_<id>",
    "versionId": "1",
    "fromTableId": "tbl_<id_1>",
    "fromRecordId": "rec_<id_a>",
    "toTableId": "tbl_<id_1>",
    "toRecordId": "rec_<id_b>",
    "relationshipTypeId": "reltyp_<id>",
    "details": {},
    "createTime": "2025-10-14T17:28:48.314Z",
    "updateTime": "2025-10-14T17:28:49.314Z"
  }
}


```

## Automating Relationship Creation

Instead of making single API calls, you can build an automated script or integration to read a list of relationship pairs and dynamically construct the JSON payload.

For example, from a CSV file containing columns for the `fromRecordId` and `toRecordId`, the script would loop through each pair, construct the JSON payload and execute a `POST` request to the relationships endpoint for every row in your file.

**For large-scale processes, it's important to implement error handling to log and manage any failed requests**, **and to respect potential API rate limits by adding small delays between calls.** This helps to ensure that thousands of relationships can be created without overwhelming the system.

Example CSV:

| fromRecordId  | toRecordId    |
| :------------ | :------------ |
| rec\_\<id\_a> | rec\_\<id\_b> |
| rec\_\<id\_c> | rec\_\<id\_d> |
| rec\_\<id\_e> | rec\_\<id\_f> |
| rec\_\<id\_g> | rec\_\<id\_h> |
| rec\_\<id\_i> | rec\_\<id\_j> |

Example Python script:

```python
import requests
import csv
import time

# --- Configuration ---
# Replace with your specific details
TENANT_NAME = "<tenant-name>"
TABLE_ID = "tbl_<id>"
RELATIONSHIP_TYPE_ID = "reltyp_<id>"
CSV_FILE_PATH = "relationships_to_create.csv"
API_KEY = "example-api-key"

# --- API Details ---
API_URL = f"https://{TENANT_NAME}.tamr.cloud/api/v1alpha1/relationships"
HEADERS = {
    "accept": "application/json",
    "X-API-KEY": API_KEY,
    "content-type": "application/json"
}

def create_relationship(from_record_id, to_record_id, row_num):
    """
    Calls the relationships API to create a single relationship.

    Args:
        from_record_id (str): The ID of the source record.
        to_record_id (str): The ID of the destination record.
        row_num (int): The current row number from the CSV for logging.
    """
    payload = {
        "fromTableId": TABLE_ID,
        "fromRecordId": from_record_id,
        "toTableId": TABLE_ID,
        "toRecordId": to_record_id,
        "relationshipTypeId": RELATIONSHIP_TYPE_ID
    }

    try:
        response = requests.post(API_URL, json=payload, headers=HEADERS)
        
        # Check if the request was successful
        if response.status_code == 200:
            print(f"SUCCESS: Row {row_num} | Relationship created from {from_record_id} to {to_record_id}")
            # print("Response:", response.json()) # Uncomment for full response details
        else:
            print(f"ERROR: Row {row_num} | Failed to create relationship for {from_record_id}.")
            print(f"Status Code: {response.status_code}")
            print(f"Response Body: {response.text}")

    except requests.exceptions.RequestException as e:
        print(f"ERROR: Row {row_num} | A network error occurred for {from_record_id}.")
        print(f"Error details: {e}")


def process_csv_and_create_relationships():
    """
    Reads the specified CSV file and initiates the relationship creation for each row.
    """
    print(f"\nStarting to process file: {CSV_FILE_PATH}...")
    try:
        with open(CSV_FILE_PATH, mode='r', encoding='utf-8') as csvfile:
            # Using DictReader to easily access columns by name
            reader = csv.DictReader(csvfile)
            
            # enumerate provides a counter (row_num starts at 2 to account for header)
            for i, row in enumerate(reader, start=2):
                from_id = row.get("fromRecordId")
                to_id = row.get("toRecordId")

                if not from_id or not to_id:
                    print(f"WARNING: Row {i} | Skipping due to missing 'fromRecordId' or 'toRecordId'.")
                    continue

                create_relationship(from_id, to_id, i)
                
                # IMPORTANT: Add a delay to avoid overwhelming the API (rate limiting). Adjust the sleep time as needed based on API limits.
   
                time.sleep(0.5)
        
        print("\nProcessing complete.")

    except FileNotFoundError:
        print(f"FATAL ERROR: The file '{CSV_FILE_PATH}' was not found.")
        print("Please ensure the CSV file is in the same directory as the script.")
    except Exception as e:
        print(f"An unexpected error occurred: {e}")


# --- Main execution block ---
if __name__ == "__main__":
    process_csv_and_create_relationships()
```

## Creating Relationships through Bulk Upload

You can configure a workflow to import relationships between records as part of a bulk process. See [Importing Relationships](https://cloud.docs.tamr.com/tamr-cloud/docs/importing-relationships) for instructions.

# Updating Existing Relationships

You  can make  a `PUT` request to [update](https://cloud.docs.tamr.com/tamr-cloud/reference/relationships_updaterelationship) relationships between two records. For example, you can link a record to a different parent in the same table.

You need the unique `relationshipTypeId` for the relationship you want to modify.

1. Construct the URL including the `relationshipId` of the relationship to update. Retrieve the `relationshipId` by using the [list relationships](https://cloud.docs.tamr.com/tamr-cloud/reference/relationships_listrelationships) endpoint.
2. Create the `payload` with the fields you want to change. In this example, we are updating the destination record (`toRecordId`).
3. Set the headers with your authentication details.

```python
import requests
url = "https://<tenant-name>.tamr.cloud/api/v1alpha1/relationships/rel_<id>"
payload = {
    "relationshipTypeId": "reltyp_<id>",
  	"fromTableId": "tbl_<id_1>",
	  "fromRecordID": "rec_<id_a>",
   	"toTableId": "tbl_<id_1>",
	  "toRecordID": "rec_<id_c>"
    
}

headers = {
    "accept": "application/json",
    "X-API-KEY": "example-api-key",
    "content-type": "application/json"
}
response = requests.put(url, json=payload, headers=headers)
print(response.text)
```

A successful request returns the full, updated relationship object.

```python
{
  "relationship": {
    "relationshipId": "rel_<id>",
    "versionId": "1",
    "fromTableId": "tbl_<id_1>",
    "fromRecordId": "rec_<id_a>",
    "toTableId": "tbl_<id_1>",
    "toRecordId": "rec_<id_c>",
    "relationshipTypeId": "reltyp_<id>",
    "details": {},
    "createTime": "2025-10-02T14:44:31.287Z",
    "updateTime": "2025-10-02T14:44:32.287Z"
  }
}

```