curl --request POST \
--url https://app.leadconduit.com/feedback \
--header 'Content-Type: application/json' \
--data '
{
"reason": "Sale Closed",
"occurred_at": "2026-05-30T08:00:00Z"
}
'import requests
url = "https://app.leadconduit.com/feedback"
payload = {
"reason": "Sale Closed",
"occurred_at": "2026-05-30T08:00:00Z"
}
headers = {"Content-Type": "application/json"}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'Content-Type': 'application/json'},
body: JSON.stringify({reason: 'Sale Closed', occurred_at: '2026-05-30T08:00:00Z'})
};
fetch('https://app.leadconduit.com/feedback', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://app.leadconduit.com/feedback",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'reason' => 'Sale Closed',
'occurred_at' => '2026-05-30T08:00:00Z'
]),
CURLOPT_HTTPHEADER => [
"Content-Type: application/json"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://app.leadconduit.com/feedback"
payload := strings.NewReader("{\n \"reason\": \"Sale Closed\",\n \"occurred_at\": \"2026-05-30T08:00:00Z\"\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://app.leadconduit.com/feedback")
.header("Content-Type", "application/json")
.body("{\n \"reason\": \"Sale Closed\",\n \"occurred_at\": \"2026-05-30T08:00:00Z\"\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://app.leadconduit.com/feedback")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["Content-Type"] = 'application/json'
request.body = "{\n \"reason\": \"Sale Closed\",\n \"occurred_at\": \"2026-05-30T08:00:00Z\"\n}"
response = http.request(request)
puts response.read_body{
"outcome": "success",
"reason": "<string>",
"price": 123,
"lead": {
"id": "5fd4371e940df5a34a3888b2",
"first_name": "Joe",
"last_name": "Blow",
"email": "joeblow@gmail.com",
"phone_1": "5125551212"
}
}{
"outcome": "success",
"reason": "<string>",
"price": 123,
"lead": {
"id": "5fd4371e940df5a34a3888b2",
"first_name": "Joe",
"last_name": "Blow",
"email": "joeblow@gmail.com",
"phone_1": "5125551212"
}
}{
"message": "Feedback not available in this flow"
}{
"message": "Event not found"
}"Not capable of generating content according to the Accept header"{
"outcome": "success",
"reason": "<string>",
"price": 123,
"lead": {
"id": "5fd4371e940df5a34a3888b2",
"first_name": "Joe",
"last_name": "Blow",
"email": "joeblow@gmail.com",
"phone_1": "5125551212"
}
}{
"outcome": "success",
"reason": "<string>",
"price": 123,
"lead": {
"id": "5fd4371e940df5a34a3888b2",
"first_name": "Joe",
"last_name": "Blow",
"email": "joeblow@gmail.com",
"phone_1": "5125551212"
}
}"Content-Type header is required"{
"error": "A Lead was ID provided, but feedback requires an event ID"
}Submit feedback for a lead
Reports what happened to a lead after delivery. Recipients use this endpoint to send
a conversion (the lead progressed through a lifecycle stage, such as Appointment Set
or Sale Closed) or a return (the lead is being given back, with the reason why).
The event_id query parameter identifies the delivery event the feedback refers to.
It is generated when a Delivery step handles the lead and must be shared with the
recipient along with the lead data. Because the event ID authorizes the request,
no API key is required.
The request body may be sent as JSON, XML, or form encoding; set the Content-Type
header accordingly, or the request is rejected. The response is JSON by default, or
XML when requested via the Accept header.
A 201 means the submission was processed, not that it was accepted. Feedback that
fails the step’s acceptance criteria, or that arrives after the lead was already
returned, also comes back 201, with outcome: "failure" in the body. Always check
outcome rather than the status code.
Feedback must be enabled on the delivery step before recipients can use this endpoint. See Enabling a Recipient to Send Conversion Feedback to LeadConduit and Sending Feedback to LeadConduit in the help center.
curl --request POST \
--url https://app.leadconduit.com/feedback \
--header 'Content-Type: application/json' \
--data '
{
"reason": "Sale Closed",
"occurred_at": "2026-05-30T08:00:00Z"
}
'import requests
url = "https://app.leadconduit.com/feedback"
payload = {
"reason": "Sale Closed",
"occurred_at": "2026-05-30T08:00:00Z"
}
headers = {"Content-Type": "application/json"}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'Content-Type': 'application/json'},
body: JSON.stringify({reason: 'Sale Closed', occurred_at: '2026-05-30T08:00:00Z'})
};
fetch('https://app.leadconduit.com/feedback', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://app.leadconduit.com/feedback",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'reason' => 'Sale Closed',
'occurred_at' => '2026-05-30T08:00:00Z'
]),
CURLOPT_HTTPHEADER => [
"Content-Type: application/json"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://app.leadconduit.com/feedback"
payload := strings.NewReader("{\n \"reason\": \"Sale Closed\",\n \"occurred_at\": \"2026-05-30T08:00:00Z\"\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://app.leadconduit.com/feedback")
.header("Content-Type", "application/json")
.body("{\n \"reason\": \"Sale Closed\",\n \"occurred_at\": \"2026-05-30T08:00:00Z\"\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://app.leadconduit.com/feedback")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["Content-Type"] = 'application/json'
request.body = "{\n \"reason\": \"Sale Closed\",\n \"occurred_at\": \"2026-05-30T08:00:00Z\"\n}"
response = http.request(request)
puts response.read_body{
"outcome": "success",
"reason": "<string>",
"price": 123,
"lead": {
"id": "5fd4371e940df5a34a3888b2",
"first_name": "Joe",
"last_name": "Blow",
"email": "joeblow@gmail.com",
"phone_1": "5125551212"
}
}{
"outcome": "success",
"reason": "<string>",
"price": 123,
"lead": {
"id": "5fd4371e940df5a34a3888b2",
"first_name": "Joe",
"last_name": "Blow",
"email": "joeblow@gmail.com",
"phone_1": "5125551212"
}
}{
"message": "Feedback not available in this flow"
}{
"message": "Event not found"
}"Not capable of generating content according to the Accept header"{
"outcome": "success",
"reason": "<string>",
"price": 123,
"lead": {
"id": "5fd4371e940df5a34a3888b2",
"first_name": "Joe",
"last_name": "Blow",
"email": "joeblow@gmail.com",
"phone_1": "5125551212"
}
}{
"outcome": "success",
"reason": "<string>",
"price": 123,
"lead": {
"id": "5fd4371e940df5a34a3888b2",
"first_name": "Joe",
"last_name": "Blow",
"email": "joeblow@gmail.com",
"phone_1": "5125551212"
}
}"Content-Type header is required"{
"error": "A Lead was ID provided, but feedback requires an event ID"
}Query Parameters
The ID of the delivery event the feedback refers to, shared with the recipient when the lead was delivered. 24 character alpha-numeric BSON identifier
^[0-9a-fA-F]{24}$"5fd4371e940df5a34a3888b2"
Body
The feedback to record for the lead.
The feedback payload a recipient sends about a delivered lead. The same fields
apply whether the body is JSON, XML (wrapped in a <feedback> root element),
or form encoded, and whether they are sent in the body of a POST or the query
string of a GET.
The kind of feedback. Use conversion when the lead progressed to a lifecycle
stage, or return when the lead is being given back.
conversion, return For a conversion, the name of the lifecycle stage the lead reached (for example
Appointment Set or Sale Closed). For a return, the reason the lead is being
returned (for example Wrong number).
Optional. A submission without a reason is accepted, but the reason is what the
step's acceptance criteria are usually written against, so omitting it will often
cause the feedback to be rejected with outcome: "failure".
"Sale Closed"
When the status actually changed in your system, as an ISO 8601 timestamp. Optional; when omitted, LeadConduit stamps the feedback with the time it was received. Use this when feedback is sent in batches, so the lifecycle date reflects the CRM event rather than the upload.
Timezone-naive values (2026-05-30T08:00:00) and date-only values
(2026-05-30) are read as UTC. A value that cannot be parsed as ISO 8601 is
ignored — the feedback is still accepted, LeadConduit falls back to receipt
time, and an occurred_at_warning variable is recorded on the
feedback-received event so the misconfiguration is visible in the event log.
"2026-05-30T08:00:00Z"
Response
The feedback submission was processed. Check the outcome field to see whether it
was accepted — a submission rejected by the step's acceptance criteria, or one sent
for a lead that was already returned, is also reported here with outcome: "failure".
The result of a feedback submission. Returned as JSON by default, or as XML
(wrapped in a <result> root element) when requested via the Accept header.
Whether the feedback was accepted. Check this field rather than the status
code — a rejected submission is still reported with 201.
success, failure, error "success"
The reason the feedback was not recorded, when the outcome is not success.
The price paid to the recipient for the lead. Present only when the delivery step priced the lead.
Identifying details of the lead the feedback applies to.
Show child attributes
Show child attributes