<?xml version="1.0" encoding="UTF-8"?>
<rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0">
  <channel>
    <title><![CDATA[Carles Salvador - Elastic Observability Labs]]></title>
    <description><![CDATA[Trusted security news & research from the team at Elastic.]]></description>
    <copyright><![CDATA[© 2026. Elasticsearch B.V. All Rights Reserved]]></copyright>
    <image>
      <title><![CDATA[Carles Salvador - Elastic Observability Labs]]></title>
      <url>https://static-www.elastic.co/v3/assets/bltefdd0b53724fa2ce/bltad972c1c27dbefc6/6a88d9782904ea5e8511d473/observability-labs-thumbnail.png</url>
      <link>https://www.elastic.co/observability-labs/author/carles-salvador</link>
    </image>
    <link>https://www.elastic.co/observability-labs/author/carles-salvador</link>
    <atom:link href="https://www.elastic.co/observability-labs/rss/author/carles-salvador.xml" rel="self" type="application/rss+xml"/>
    <language><![CDATA[en]]></language>
    <lastBuildDate>Tue, 13 Oct 2026 16:52:59 GMT</lastBuildDate>
  <item>
    <title><![CDATA[From Uptime to Synthetics in Elastic: Your migration Playbook]]></title>
    <description><![CDATA[Effortlessly migrate your existing Uptime TCP, ICMP, and HTTP monitors to Elastic Synthetics with this comprehensive guide, leveraging Private Locations and Synthetics Projects for efficient, future-proof monitoring.]]></description>
    <content:encoded><![CDATA[<p>Have you seen the warning that Uptime is deprecated and want to know how to easily migrate to Synthetics? Then you are in the right place. 
Starting with version 8.15.0, uptime checks have been deprecated in favor of synthetic monitoring.</p>
<p>Many users may have a large number of TCP, ICMP, and HTTP monitors and need to migrate them to Synthetics. In this guide, we will explain how to perform this migration easily while ensuring that it will be future-proof or able to develop more advanced checks such as <a href="https://www.elastic.co/docs/solutions/observability/synthetics/#monitoring-synthetics">Browser monitors</a>.</p>
<p>First, we must consider the number of monitors to migrate; if the number is small, the easiest way would be to do it manually through the <a href="https://www.elastic.co/docs/solutions/observability/synthetics/create-monitors-ui">Synthetics UI</a>. However, in this guide we will assume that we have dozens or hundreds of monitors to migrate, and doing it manually in the Synthetics UI is not an option.</p>
<h2 id="privatelocation">Private Location</h2>
<p>Traditionally, uptime monitors required a <a href="https://www.elastic.co/docs/reference/beats/heartbeat/">Heartbeat</a> to be deployed in your infrastructure, which indirectly allowed you to monitor endpoints or hosts on your private network. If this is still a requirement, you will need to either configure <a href="https://www.elastic.co/docs/solutions/observability/synthetics/monitor-resources-on-private-networks">Private Location</a> or allow Elastic’s global managed infrastructure to <a href="https://www.elastic.co/docs/solutions/observability/synthetics/monitor-resources-on-private-networks#monitor-via-access-control">access your private endpoints</a> (only on <a href="https://www.elastic.co/docs/deploy-manage/deploy/elastic-cloud/cloud-hosted">ECH</a> &amp; <a href="https://www.elastic.co/docs/deploy-manage/deploy/elastic-cloud/serverless">Serverless</a>).</p>
<p>In this guide, we will use Private Locations, which will allow you to monitor both internal and external resources. More details can be found here: <a href="https://www.elastic.co/docs/solutions/observability/synthetics/monitor-resources-on-private-networks#monitor-via-private-agent">Monitor resources on private networks</a></p>
<h3 id="step1setupfleetserverandelasticagent">Step 1: Set up Fleet Server and Elastic Agent</h3>
<p>Private Locations are simply Elastic Agents enrolled in Fleet and managed through an agent policy. </p>
<p>If you don't have a Fleet Server yet, start <a href="https://www.elastic.co/docs/reference/fleet/fleet-server">setting up a Fleet Server</a>. This step is not necessary if you use ECH, as it comes by default.</p>
<p>Next, you will need to create an Agent Policy. Go to <strong>Observability → Monitors (Synthetics) → Settings (top right) → Private Location → + Create Location</strong></p>
<p><img src="https://static-www.elastic.co/v3/assets/bltefdd0b53724fa2ce/blt64b587cc01e23833/6a7f1bf7fc63ab348a64d0a6/create-private-location.png" alt="Create Private Location" /></p>
<p>Fill in the fields and create a new policy for this Private Location. It is important to know that Private Location should be set up against an agent policy that runs on a <strong>single</strong> Elastic Agent. </p>
<h3 id="step2deploytheelasticagent">Step 2: Deploy the Elastic Agent</h3>
<p>Now we need to deploy the Elastic Agent that will be responsible for running all the monitors. We can use the same host we were using for Heartbeat. There is only one requirement: we must be able to run Docker containers, since to take advantage of all the features of Synthetics, we must use the <code>elastic-agent-complete</code> Docker Image.</p>
<ol>
<li><p>Go to <strong>Fleet –&gt; Enrollment tokens</strong> and note the enrollment token relevant to the policy you just created for the Private Location. Now go to <strong>Settings</strong> and note the default Fleet server host URL.</p></li>
<li><p>On the host, run the following commands. For more information on running Elastic Agent with Docker, refer to Run Elastic Agent in a container.</p></li>
</ol>
<pre><code>docker run \
&amp;nbsp;&amp;nbsp;--env FLEET_ENROLL=1 \
&amp;nbsp;&amp;nbsp;--env FLEET_URL={fleet_server_host_url} \
&amp;nbsp;&amp;nbsp;--env FLEET_ENROLLMENT_TOKEN={enrollment_token} \
&amp;nbsp;&amp;nbsp;--cap-add=NET_RAW \
&amp;nbsp;&amp;nbsp;--cap-add=SETUID \
&amp;nbsp;&amp;nbsp;--rm docker.elastic.co/elastic-agent/elastic-agent-complete:9.3.2
</code></pre>
<h2 id="syntheticproject">Synthetic Project</h2>
<p>At this point, we already have the location from which our Synthetic monitors will run. Now we need to load our Uptime monitors as Synthetics.</p>
<p>As we mentioned earlier, there are two ways to do this: either manually through the Synthetics UI or through a Synthetics Project.
In our case, since we have so many monitors to migrate and don't want to do it manually, we will use <a href="https://www.elastic.co/docs/solutions/observability/synthetics/create-monitors-with-projects">Synthetics Projects</a>. </p>
<p>The great thing about Synthetics Project is that it has some backward compatibility with the definition of monitors in <code>heartbeat.yml</code> and we will be leveraging it.</p>
<h3 id="whatssyntheticsproject">What's Synthetics project?</h3>
<p>Synthetics project is the most powerful and flexible way to manage synthetic monitors in Elastic, based on the Infrastructure as Code principle and compatible with Git-Ops flows. Instead of configuring monitors from the interface, you define them as code: .yml files for lightweight monitors and JavaScript or TypeScript scripts for browser-type monitors (journeys).</p>
<p>This approach allows you to structure your monitors in a repository, version them with Git, validate them, and deploy them automatically using CI/CD flows, providing traceability, reviews, and consistent deployments.</p>
<h3 id="step3initializeyoursyntheticsproject">Step 3: Initialize your Synthetics project</h3>
<p>You will no longer need to connect to the hosts where you deployed the Elastic Agent, as the remaining steps can be performed locally as long as you have connectivity to Kibana!</p>
<p>Since Synthetics Projects is based on Node.js, make sure you have it <a href="https://nodejs.org/en/download">installed</a>. </p>
<ol>
<li>Install the package:</li>
</ol>
<pre><code>npm install -g @elastic/synthetics
</code></pre>
<ol>
<li>Confirm your system is setup correctly:</li>
</ol>
<pre><code>npx @elastic/synthetics -h
</code></pre>
<ol>
<li>Start by creating your first Synthetics project. Run the command below to create a new Synthetics project named <code>synthetic-project-test</code> in the current directory.</li>
</ol>
<pre><code>npx @elastic/synthetics init synthetic-project-test
</code></pre>
<ol>
<li><p>Follow the prompt instructions to configure the default variables for your Synthetics project. Make sure to at least <strong>select your Private Location.</strong> Once that’s done, set the <code>SYNTHETICS_API_KEY</code> environment variable in your terminal, which allows the project to authenticate with Kibana.</p></li>
<li><p>To generate an API key go to Synthetics Kibana.</p></li>
<li><p>Click <strong>Settings</strong>.</p></li>
<li><p>Switch to the <strong>Project API Keys</strong> tab.</p></li>
<li><p>Click <strong>Generate Project API key</strong>.</p></li>
</ol>
<p><img src="https://static-www.elastic.co/v3/assets/bltefdd0b53724fa2ce/bltbf4abd9defe75bad/6a7f1bfa73d9bd03a929df94/generate-api-key.png" alt="Generate API Key" /></p>
<p>More details for all the steps can be found here: <a href="https://www.elastic.co/docs/solutions/observability/synthetics/create-monitors-with-projects#synthetics-get-started-project-create-a-synthetics-project">Create monitors with a Synthetics project</a></p>
<h3 id="step4addyourheartbeatymlfiles">Step 4: Add your <code>heartbeat.yml</code> files</h3>
<p>Once the project is initialized, access the folder it has created and take a look at the project structure:</p>
<ul>
<li><p><code>journeys</code> is where you’ll add .ts and .js files defining your browser monitors. It currently contains files defining sample monitors.</p></li>
<li><p><code>lightweight</code> is where we’ll add our heartbeat.yml files defining our lightweight monitors. It currently contains a file defining sample monitors.</p></li>
</ul>
<p>Therefore, all we have to do is copy our <code>heartbeat.yml</code> files to this lightweight folder. Before copying <code>heartbeat.yml</code>, keep in mind that we don't need all the content, we are only interested in the <code>heartbeat.monitors</code> part. \
We recommend considering splitting the file into logical groups. Instead of maintaining a single large YAML file, you could create multiple smaller YAML files, with each file representing either a single check or a group of related checks. This approach may simplify management and improve compatibility with GitOps workflows.\
Each YAML file should look like this:</p>
<pre><code>carles@synthetics-migration:synthetic-project-test/lightweight# cat heartbeat.yml

heartbeat.monitors:
- type: icmp
&amp;nbsp;&amp;nbsp;schedule: '@every 10s'
&amp;nbsp;&amp;nbsp;hosts: ["localhost"]
&amp;nbsp;&amp;nbsp;id: my-icmp-service-synth
&amp;nbsp;&amp;nbsp;name: My ICMP Service - Synthetic
- type: tcp
&amp;nbsp;&amp;nbsp;schedule: '@every 10s'
&amp;nbsp;&amp;nbsp;hosts: ["myremotehost:8123"]
&amp;nbsp;&amp;nbsp;mode: any
&amp;nbsp;&amp;nbsp;id: my-tcp-service-synth
&amp;nbsp;&amp;nbsp;name: My TCP Service Synthetic
- type: http
&amp;nbsp;&amp;nbsp;schedule: '@every 10s'
&amp;nbsp;&amp;nbsp;urls: ["http://elastic.co"]
&amp;nbsp;&amp;nbsp;id: my-http-service-synth
&amp;nbsp;&amp;nbsp;name: My HTTP Service Synthetic
</code></pre>
<p>What we just did is define different ICMP, TCP, and HTTP checks as code.</p>
<p>Now we need to ask Synthetics project to create the monitors in Kibana based on what we have defined in our YAML files:</p>
<pre><code>npx @elastic/synthetics push --auth $SYNTHETICS_API_KEY --url &lt;kibana-url&gt;
</code></pre>
<p>Unfortunately, we do not support a 1-to-1 mapping of the heartbeat schema to the lightweight schema, so you may encounter some errors during the execution of this command. One example is the definition of <code>schedule</code>. Heartbeat supports the use of crontab expressions, but Project requires the use of <code>@every</code> syntax.</p>
<p>If no syntax errors were found, the command output will show that the monitors have been successfully created in Kibana!</p>
<p>Then, go to <strong>Synthetics</strong> in Kibana. You should see your newly pushed monitors running. You can also go to the Management tab to see the monitors' configuration settings.</p>]]></content:encoded>
    <link>https://www.elastic.co/observability-labs/blog/uptime-to-synthetics-guide</link>
    <guid isPermaLink="false">uptime-to-synthetics-guide</guid>
    <category><![CDATA[Incident Management]]></category>
    <dc:creator><![CDATA[Carles Salvador]]></dc:creator>
    <enclosure url="https://static-www.elastic.co/v3/assets/bltefdd0b53724fa2ce/blt77a5b002e5de61f1/6a7f1bfde02fac67655d69d9/blog-header.png" length="0" type="image/png"/>
    <pubDate>Thu, 11 Sep 2025 00:00:00 GMT</pubDate>
  </item>
  </channel>
</rss>