PUT /v1/tables/{id}/customMetric
from metadata.sdk import configure, client
from metadata.sdk.entities import Tables
from metadata.generated.schema.api.tests.createCustomMetric import CreateCustomMetricRequest
configure(
host="https://your-company.open-metadata.org/api",
jwt_token="your-jwt-token"
)
rest = client().ometa.client
table_id = "a1b2c3d4-e5f6-7890-abcd-ef1234567890"
# Add a table-level custom metric
Tables.add_custom_metric(table_id, CreateCustomMetricRequest(
name="active_customer_ratio",
description="Ratio of active customers to total customers",
expression="SELECT CAST(SUM(CASE WHEN active = true THEN 1 ELSE 0 END) AS FLOAT) / COUNT(*) FROM {table}"
))
# Add a column-level custom metric
Tables.add_custom_metric(table_id, CreateCustomMetricRequest(
name="email_domain_count",
description="Number of distinct email domains",
columnName="email",
expression="SELECT COUNT(DISTINCT SPLIT_PART(email, '@', 2)) FROM {table}"
))
# Delete a table-level custom metric
rest.delete(f"/tables/{table_id}/customMetric/active_customer_ratio")
# Delete a column-level custom metric
rest.delete(f"/tables/{table_id}/customMetric/email/email_domain_count")
import org.openmetadata.schema.tests.CustomMetric;
// client is an initialized OpenMetadataClient.
String tableId = "a1b2c3d4-e5f6-7890-abcd-ef1234567890";
// Add a table-level custom metric
CustomMetric tableMetric = new CustomMetric()
.withName("active_customer_ratio")
.withDescription("Ratio of active customers to total customers")
.withExpression("SELECT CAST(SUM(CASE WHEN active = true THEN 1 ELSE 0 END) AS FLOAT) / COUNT(*) FROM {table}");
client.tables().updateCustomMetric(tableId, tableMetric);
// Add a column-level custom metric
CustomMetric columnMetric = new CustomMetric()
.withName("email_domain_count")
.withDescription("Number of distinct email domains")
.withColumnName("email")
.withExpression("SELECT COUNT(DISTINCT SPLIT_PART(email, '@', 2)) FROM {table}");
client.tables().updateCustomMetric(tableId, columnMetric);
// Delete a table-level custom metric
client.tables().deleteCustomMetric(tableId, "active_customer_ratio");
// Delete a column-level custom metric
client.tables().deleteCustomMetric(tableId, "email/email_domain_count");
# Add a table-level custom metric
curl -X PUT "{base_url}/api/v1/tables/455e3d9d-dbbf-455e-b3be-7191daa825f3/customMetric" \
-H "Authorization: Bearer {access_token}" \
-H "Content-Type: application/json" \
-d '{
"name": "high_performer_ratio",
"description": "Ratio of high-performing agents (score > 90) to total agents",
"expression": "SELECT CAST(SUM(CASE WHEN performance_score > 90 THEN 1 ELSE 0 END) AS FLOAT) / COUNT(*) FROM {table}"
}'
# Add a column-level custom metric
curl -X PUT "{base_url}/api/v1/tables/455e3d9d-dbbf-455e-b3be-7191daa825f3/customMetric" \
-H "Authorization: Bearer {access_token}" \
-H "Content-Type: application/json" \
-d '{
"name": "avg_performance",
"description": "Average performance score across all agents",
"columnName": "performance_score",
"expression": "SELECT AVG(performance_score) FROM {table}"
}'
# Delete a custom metric
curl -X DELETE "{base_url}/api/v1/tables/455e3d9d-dbbf-455e-b3be-7191daa825f3/customMetric/high_performer_ratio" \
-H "Authorization: Bearer {access_token}"
{
"id": "455e3d9d-dbbf-455e-b3be-7191daa825f3",
"name": "agent_performance_summary",
"fullyQualifiedName": "sample_data.ecommerce_db.shopify.agent_performance_summary",
"customMetrics": [
{
"name": "high_performer_ratio",
"description": "Ratio of high-performing agents (score > 90) to total agents",
"expression": "SELECT CAST(SUM(CASE WHEN performance_score > 90 THEN 1 ELSE 0 END) AS FLOAT) / COUNT(*) FROM {table}"
}
]
}
Custom Metrics
Add and delete custom metrics for tables
PUT
/
v1
/
tables
/
{id}
/
customMetric
PUT /v1/tables/{id}/customMetric
from metadata.sdk import configure, client
from metadata.sdk.entities import Tables
from metadata.generated.schema.api.tests.createCustomMetric import CreateCustomMetricRequest
configure(
host="https://your-company.open-metadata.org/api",
jwt_token="your-jwt-token"
)
rest = client().ometa.client
table_id = "a1b2c3d4-e5f6-7890-abcd-ef1234567890"
# Add a table-level custom metric
Tables.add_custom_metric(table_id, CreateCustomMetricRequest(
name="active_customer_ratio",
description="Ratio of active customers to total customers",
expression="SELECT CAST(SUM(CASE WHEN active = true THEN 1 ELSE 0 END) AS FLOAT) / COUNT(*) FROM {table}"
))
# Add a column-level custom metric
Tables.add_custom_metric(table_id, CreateCustomMetricRequest(
name="email_domain_count",
description="Number of distinct email domains",
columnName="email",
expression="SELECT COUNT(DISTINCT SPLIT_PART(email, '@', 2)) FROM {table}"
))
# Delete a table-level custom metric
rest.delete(f"/tables/{table_id}/customMetric/active_customer_ratio")
# Delete a column-level custom metric
rest.delete(f"/tables/{table_id}/customMetric/email/email_domain_count")
import org.openmetadata.schema.tests.CustomMetric;
// client is an initialized OpenMetadataClient.
String tableId = "a1b2c3d4-e5f6-7890-abcd-ef1234567890";
// Add a table-level custom metric
CustomMetric tableMetric = new CustomMetric()
.withName("active_customer_ratio")
.withDescription("Ratio of active customers to total customers")
.withExpression("SELECT CAST(SUM(CASE WHEN active = true THEN 1 ELSE 0 END) AS FLOAT) / COUNT(*) FROM {table}");
client.tables().updateCustomMetric(tableId, tableMetric);
// Add a column-level custom metric
CustomMetric columnMetric = new CustomMetric()
.withName("email_domain_count")
.withDescription("Number of distinct email domains")
.withColumnName("email")
.withExpression("SELECT COUNT(DISTINCT SPLIT_PART(email, '@', 2)) FROM {table}");
client.tables().updateCustomMetric(tableId, columnMetric);
// Delete a table-level custom metric
client.tables().deleteCustomMetric(tableId, "active_customer_ratio");
// Delete a column-level custom metric
client.tables().deleteCustomMetric(tableId, "email/email_domain_count");
# Add a table-level custom metric
curl -X PUT "{base_url}/api/v1/tables/455e3d9d-dbbf-455e-b3be-7191daa825f3/customMetric" \
-H "Authorization: Bearer {access_token}" \
-H "Content-Type: application/json" \
-d '{
"name": "high_performer_ratio",
"description": "Ratio of high-performing agents (score > 90) to total agents",
"expression": "SELECT CAST(SUM(CASE WHEN performance_score > 90 THEN 1 ELSE 0 END) AS FLOAT) / COUNT(*) FROM {table}"
}'
# Add a column-level custom metric
curl -X PUT "{base_url}/api/v1/tables/455e3d9d-dbbf-455e-b3be-7191daa825f3/customMetric" \
-H "Authorization: Bearer {access_token}" \
-H "Content-Type: application/json" \
-d '{
"name": "avg_performance",
"description": "Average performance score across all agents",
"columnName": "performance_score",
"expression": "SELECT AVG(performance_score) FROM {table}"
}'
# Delete a custom metric
curl -X DELETE "{base_url}/api/v1/tables/455e3d9d-dbbf-455e-b3be-7191daa825f3/customMetric/high_performer_ratio" \
-H "Authorization: Bearer {access_token}"
{
"id": "455e3d9d-dbbf-455e-b3be-7191daa825f3",
"name": "agent_performance_summary",
"fullyQualifiedName": "sample_data.ecommerce_db.shopify.agent_performance_summary",
"customMetrics": [
{
"name": "high_performer_ratio",
"description": "Ratio of high-performing agents (score > 90) to total agents",
"expression": "SELECT CAST(SUM(CASE WHEN performance_score > 90 THEN 1 ELSE 0 END) AS FLOAT) / COUNT(*) FROM {table}"
}
]
}
Custom Metrics
Define custom SQL-based metrics on a table or specific column. Custom metrics are evaluated during profiling runs and tracked over time.Add Custom Metric
PUT /v1/tables/{id}/customMetric
string
required
UUID of the table.
string
required
Name of the custom metric. Must be unique within the table.
string
required
SQL expression to evaluate for this metric. Must return a single numeric value.
string
Name of the column this metric applies to. If omitted, the metric is table-level.
string
Description of what this metric measures.
Delete Custom Metric
DELETE /v1/tables/{id}/customMetric/{metricName}
To delete a column-level metric, use DELETE /v1/tables/{id}/customMetric/{columnName}/{metricName}.
string
required
UUID of the table.
string
required
Name of the custom metric to delete.
PUT /v1/tables/{id}/customMetric
from metadata.sdk import configure, client
from metadata.sdk.entities import Tables
from metadata.generated.schema.api.tests.createCustomMetric import CreateCustomMetricRequest
configure(
host="https://your-company.open-metadata.org/api",
jwt_token="your-jwt-token"
)
rest = client().ometa.client
table_id = "a1b2c3d4-e5f6-7890-abcd-ef1234567890"
# Add a table-level custom metric
Tables.add_custom_metric(table_id, CreateCustomMetricRequest(
name="active_customer_ratio",
description="Ratio of active customers to total customers",
expression="SELECT CAST(SUM(CASE WHEN active = true THEN 1 ELSE 0 END) AS FLOAT) / COUNT(*) FROM {table}"
))
# Add a column-level custom metric
Tables.add_custom_metric(table_id, CreateCustomMetricRequest(
name="email_domain_count",
description="Number of distinct email domains",
columnName="email",
expression="SELECT COUNT(DISTINCT SPLIT_PART(email, '@', 2)) FROM {table}"
))
# Delete a table-level custom metric
rest.delete(f"/tables/{table_id}/customMetric/active_customer_ratio")
# Delete a column-level custom metric
rest.delete(f"/tables/{table_id}/customMetric/email/email_domain_count")
import org.openmetadata.schema.tests.CustomMetric;
// client is an initialized OpenMetadataClient.
String tableId = "a1b2c3d4-e5f6-7890-abcd-ef1234567890";
// Add a table-level custom metric
CustomMetric tableMetric = new CustomMetric()
.withName("active_customer_ratio")
.withDescription("Ratio of active customers to total customers")
.withExpression("SELECT CAST(SUM(CASE WHEN active = true THEN 1 ELSE 0 END) AS FLOAT) / COUNT(*) FROM {table}");
client.tables().updateCustomMetric(tableId, tableMetric);
// Add a column-level custom metric
CustomMetric columnMetric = new CustomMetric()
.withName("email_domain_count")
.withDescription("Number of distinct email domains")
.withColumnName("email")
.withExpression("SELECT COUNT(DISTINCT SPLIT_PART(email, '@', 2)) FROM {table}");
client.tables().updateCustomMetric(tableId, columnMetric);
// Delete a table-level custom metric
client.tables().deleteCustomMetric(tableId, "active_customer_ratio");
// Delete a column-level custom metric
client.tables().deleteCustomMetric(tableId, "email/email_domain_count");
# Add a table-level custom metric
curl -X PUT "{base_url}/api/v1/tables/455e3d9d-dbbf-455e-b3be-7191daa825f3/customMetric" \
-H "Authorization: Bearer {access_token}" \
-H "Content-Type: application/json" \
-d '{
"name": "high_performer_ratio",
"description": "Ratio of high-performing agents (score > 90) to total agents",
"expression": "SELECT CAST(SUM(CASE WHEN performance_score > 90 THEN 1 ELSE 0 END) AS FLOAT) / COUNT(*) FROM {table}"
}'
# Add a column-level custom metric
curl -X PUT "{base_url}/api/v1/tables/455e3d9d-dbbf-455e-b3be-7191daa825f3/customMetric" \
-H "Authorization: Bearer {access_token}" \
-H "Content-Type: application/json" \
-d '{
"name": "avg_performance",
"description": "Average performance score across all agents",
"columnName": "performance_score",
"expression": "SELECT AVG(performance_score) FROM {table}"
}'
# Delete a custom metric
curl -X DELETE "{base_url}/api/v1/tables/455e3d9d-dbbf-455e-b3be-7191daa825f3/customMetric/high_performer_ratio" \
-H "Authorization: Bearer {access_token}"
{
"id": "455e3d9d-dbbf-455e-b3be-7191daa825f3",
"name": "agent_performance_summary",
"fullyQualifiedName": "sample_data.ecommerce_db.shopify.agent_performance_summary",
"customMetrics": [
{
"name": "high_performer_ratio",
"description": "Ratio of high-performing agents (score > 90) to total agents",
"expression": "SELECT CAST(SUM(CASE WHEN performance_score > 90 THEN 1 ELSE 0 END) AS FLOAT) / COUNT(*) FROM {table}"
}
]
}
Returns
Add returns the updated table object with the custom metric included. Delete returns no content (204).Response
array
Error Handling
| Code | Error Type | Description |
|---|---|---|
401 | UNAUTHORIZED | Invalid or missing authentication token |
403 | FORBIDDEN | User lacks permission |
404 | NOT_FOUND | Table or custom metric does not exist |
400 | BAD_REQUEST | Invalid metric definition or SQL expression |
409 | CONFLICT | Custom metric with same name already exists |
Was this page helpful?