Create Note
curl --request POST \
--url https://api.usecobalt.com/v1/notes \
--header 'Content-Type: application/json' \
--header 'access_token: <api-key>' \
--header 'client_id: <api-key>' \
--header 'client_secret: <api-key>' \
--data '
{
"appointment_id": "<string>",
"note": "<string>",
"icd_10_codes": [
"<string>"
],
"cpt_codes": [
"<string>"
]
}
'import requests
url = "https://api.usecobalt.com/v1/notes"
payload = {
"appointment_id": "<string>",
"note": "<string>",
"icd_10_codes": ["<string>"],
"cpt_codes": ["<string>"]
}
headers = {
"client_id": "<api-key>",
"client_secret": "<api-key>",
"access_token": "<api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {
client_id: '<api-key>',
client_secret: '<api-key>',
access_token: '<api-key>',
'Content-Type': 'application/json'
},
body: JSON.stringify({
appointment_id: '<string>',
note: '<string>',
icd_10_codes: ['<string>'],
cpt_codes: ['<string>']
})
};
fetch('https://api.usecobalt.com/v1/notes', 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://api.usecobalt.com/v1/notes",
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([
'appointment_id' => '<string>',
'note' => '<string>',
'icd_10_codes' => [
'<string>'
],
'cpt_codes' => [
'<string>'
]
]),
CURLOPT_HTTPHEADER => [
"Content-Type: application/json",
"access_token: <api-key>",
"client_id: <api-key>",
"client_secret: <api-key>"
],
]);
$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://api.usecobalt.com/v1/notes"
payload := strings.NewReader("{\n \"appointment_id\": \"<string>\",\n \"note\": \"<string>\",\n \"icd_10_codes\": [\n \"<string>\"\n ],\n \"cpt_codes\": [\n \"<string>\"\n ]\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("client_id", "<api-key>")
req.Header.Add("client_secret", "<api-key>")
req.Header.Add("access_token", "<api-key>")
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://api.usecobalt.com/v1/notes")
.header("client_id", "<api-key>")
.header("client_secret", "<api-key>")
.header("access_token", "<api-key>")
.header("Content-Type", "application/json")
.body("{\n \"appointment_id\": \"<string>\",\n \"note\": \"<string>\",\n \"icd_10_codes\": [\n \"<string>\"\n ],\n \"cpt_codes\": [\n \"<string>\"\n ]\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.usecobalt.com/v1/notes")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["client_id"] = '<api-key>'
request["client_secret"] = '<api-key>'
request["access_token"] = '<api-key>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"appointment_id\": \"<string>\",\n \"note\": \"<string>\",\n \"icd_10_codes\": [\n \"<string>\"\n ],\n \"cpt_codes\": [\n \"<string>\"\n ]\n}"
response = http.request(request)
puts response.read_body{
"success": true,
"message": "<string>"
}Notes
Create Note
Creates a note for a given appointment.
POST
/
notes
Create Note
curl --request POST \
--url https://api.usecobalt.com/v1/notes \
--header 'Content-Type: application/json' \
--header 'access_token: <api-key>' \
--header 'client_id: <api-key>' \
--header 'client_secret: <api-key>' \
--data '
{
"appointment_id": "<string>",
"note": "<string>",
"icd_10_codes": [
"<string>"
],
"cpt_codes": [
"<string>"
]
}
'import requests
url = "https://api.usecobalt.com/v1/notes"
payload = {
"appointment_id": "<string>",
"note": "<string>",
"icd_10_codes": ["<string>"],
"cpt_codes": ["<string>"]
}
headers = {
"client_id": "<api-key>",
"client_secret": "<api-key>",
"access_token": "<api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {
client_id: '<api-key>',
client_secret: '<api-key>',
access_token: '<api-key>',
'Content-Type': 'application/json'
},
body: JSON.stringify({
appointment_id: '<string>',
note: '<string>',
icd_10_codes: ['<string>'],
cpt_codes: ['<string>']
})
};
fetch('https://api.usecobalt.com/v1/notes', 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://api.usecobalt.com/v1/notes",
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([
'appointment_id' => '<string>',
'note' => '<string>',
'icd_10_codes' => [
'<string>'
],
'cpt_codes' => [
'<string>'
]
]),
CURLOPT_HTTPHEADER => [
"Content-Type: application/json",
"access_token: <api-key>",
"client_id: <api-key>",
"client_secret: <api-key>"
],
]);
$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://api.usecobalt.com/v1/notes"
payload := strings.NewReader("{\n \"appointment_id\": \"<string>\",\n \"note\": \"<string>\",\n \"icd_10_codes\": [\n \"<string>\"\n ],\n \"cpt_codes\": [\n \"<string>\"\n ]\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("client_id", "<api-key>")
req.Header.Add("client_secret", "<api-key>")
req.Header.Add("access_token", "<api-key>")
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://api.usecobalt.com/v1/notes")
.header("client_id", "<api-key>")
.header("client_secret", "<api-key>")
.header("access_token", "<api-key>")
.header("Content-Type", "application/json")
.body("{\n \"appointment_id\": \"<string>\",\n \"note\": \"<string>\",\n \"icd_10_codes\": [\n \"<string>\"\n ],\n \"cpt_codes\": [\n \"<string>\"\n ]\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.usecobalt.com/v1/notes")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["client_id"] = '<api-key>'
request["client_secret"] = '<api-key>'
request["access_token"] = '<api-key>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"appointment_id\": \"<string>\",\n \"note\": \"<string>\",\n \"icd_10_codes\": [\n \"<string>\"\n ],\n \"cpt_codes\": [\n \"<string>\"\n ]\n}"
response = http.request(request)
puts response.read_body{
"success": true,
"message": "<string>"
}Use the Cobalt
appointment_id. The appointment_id parameter should be the Cobalt appointment ID returned from API responses or GET endpoints, not the EHR appointment ID.Formatting Note Content
When providing thenote content, it’s important to use \n for line breaks if you want those line breaks to be reflected in the EMR. For example, if you want the note to appear in the EMR as:
SUBJECTIVE:
this is the subjective section
OBJECTIVE:
this is the objective section
ASSESSMENT:
this is the assessment section
PLAN:
this is the plan section
note field:
"SUBJECTIVE:\nthis is the subjective section\n\nOBJECTIVE:\nthis is the objective section\n\nASSESSMENT\nthis is the assessment section\n\nPLAN: this is the plan section"
Note Content Formats
Thenote parameter accepts two different formats depending on your EMR integration:
- String format (default): A single text string with
\nline breaks - Structured object format (eClinicalWorks): An object with separate fields for clinical documentation, along with optional ICD-10 and CPT codes
Example Request (String Format)
curl -X POST https://api.usecobalt.com/v1/notes \
-H 'Content-Type: application/json' \
-H 'client_id: ci_live_198908HJDKJSH98789OHKJL' \
-H 'client_secret: cs_live_9827hofdsklOYYHJLJh' \
-H 'access_token: 493JKLHIU98789hLKH9HHJH' \
-d '{
"appointment_id": "728948",
"note": "SUBJECTIVE:\nthis is the subjective section\n\nOBJECTIVE:\nthis is the objective section\n\nASSESSMENT\nthis is the assessment section\n\nPLAN: this is the plan section"
}'
Example Request (Structured Format for eClinicalWorks)
curl -X POST https://api.usecobalt.com/v1/notes \
-H 'Content-Type: application/json' \
-H 'client_id: ci_live_198908HJDKJSH98789OHKJL' \
-H 'client_secret: cs_live_9827hofdsklOYYHJLJh' \
-H 'access_token: 493JKLHIU98789hLKH9HHJH' \
-d '{
"appointment_id": "728948",
"note": {
"hpi": "Patient presents with persistent lower back pain for 2 weeks. Pain is described as dull and achy, rated 6/10. Worse with prolonged sitting and bending forward. Denies radiation to legs, numbness, or tingling. No bowel or bladder changes. Patient tried over-the-counter ibuprofen with minimal relief.",
"exam": "Vital signs: BP 128/82, HR 74, Temp 98.6°F. General: Alert and oriented x3, in no acute distress. MSK: Limited range of motion in lumbar spine with forward flexion. Tenderness to palpation over L4-L5 region. Negative straight leg raise bilaterally. Motor strength 5/5 in bilateral lower extremities. Sensation intact.",
"assessment": "Acute mechanical low back pain, likely lumbar strain. No red flags for serious pathology.",
"treatment": "Prescribed naproxen 500mg BID for 10 days. Recommended ice/heat therapy alternating every 20 minutes. Physical therapy referral placed for core strengthening and flexibility exercises. Patient educated on proper lifting mechanics and posture. Return precautions discussed including progressive neurological symptoms."
},
"icd_10_codes": ["M54.5", "M54.50"],
"cpt_codes": ["99213", "97110"]
}'
Example Response
{
"success": true,
"message": "Note upload in progress. A webhook event will be sent upon completion.",
"job_id": 12345
}
Webhook Notifications
When the note processing is complete, we will send a webhook to your registered endpoint. Here are examples of what those webhook payloads will look like: See the Webhook Events reference for the full field breakdown and error codes.Success
{
"id": "evt_1J9X2q2eZvKYlo2CluR9g9gV",
"access_token_reference_id": "user_1J9X2q2eZvKYlo2Cxyz",
"object": "event",
"created": "2023-10-27T10:30:00Z",
"type": "note.uploaded",
"job_id": 12345,
"data": {
"appointment_id": "728948",
"mrn": "12345",
"timezone": "America/New_York",
"status": "partial_success",
"icd_codes": {
"matched": [
{ "code": "E11.9", "name": "Type 2 diabetes mellitus without complications" }
],
"unmatched": [
{ "code": "Z00.00", "reason": "Code not found in EHR system" }
]
},
"cpt_codes": {
"matched": [
{ "code": "99213", "name": "Office/outpatient visit, established patient" }
],
"unmatched": []
}
}
}
Failure
{
"id": "evt_1J9X2q2eZvKYlo2CluR9g9gW",
"access_token_reference_id": "user_1J9X2q2eZvKYlo2Cxyz",
"object": "event",
"created": "2023-10-27T10:35:00Z",
"type": "note.failed",
"job_id": 12345,
"data": {
"appointment_id": "728948",
"mrn": "12345",
"status": "failed",
"failure_reason": "Text contains \"]]>\" which cannot be used in CDATA blocks. Please remove this sequence from the note text.",
"reasons": [
{
"code": "UNSUPPORTED_CHARACTERS",
"description": "Text contains \"]]>\" which cannot be used in CDATA blocks. Please remove this sequence from the note text."
}
]
}
}
Authorizations
Body
application/json
The id of the appointment. This is the id included in the response to GET /appointments.
The data for the note. Can be either a string or structured object depending on EMR integration.
Optional ICD-10 diagnosis codes (only used with structured note format)
Optional CPT procedure codes (only used with structured note format)
⌘I