<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Mecanik Dev</title>
    <description>The latest articles on DEV Community by Mecanik Dev (mecanik-dev).</description>
    <link>https://dev.to/mecanik-dev</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Forganization%2Fprofile_image%2F14267%2Fbd937a40-59d7-4933-983d-716f80e172b4.png</url>
      <title>DEV Community: Mecanik Dev</title>
      <link>https://dev.to/mecanik-dev</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/mecanik-dev"/>
    <language>en</language>
    <item>
      <title>Securing Linux Servers with CSF: The Ultimate Guide for 2023</title>
      <dc:creator>Mecanik1337</dc:creator>
      <pubDate>Wed, 07 Oct 2026 18:00:00 +0000</pubDate>
      <link>https://dev.to/mecanik-dev/securing-linux-servers-with-csf-the-ultimate-guide-for-2023-21kl</link>
      <guid>https://dev.to/mecanik-dev/securing-linux-servers-with-csf-the-ultimate-guide-for-2023-21kl</guid>
      <description>&lt;p&gt;Linux servers have gained tremendous popularity among businesses and individuals due to their flexibility, cost-effectiveness, and powerful performance. However, ensuring the security of these servers is of paramount importance.&lt;/p&gt;

&lt;p&gt;In this article, we'll explore how to secure Linux servers using CSF (ConfigServer Security &amp;amp; Firewall) or similar software, and provide you with links and examples to fortify your server.&lt;/p&gt;

&lt;h2&gt;
  
  
  What is CSF?
&lt;/h2&gt;

&lt;p&gt;CSF is a powerful, stateful firewall that is specifically designed for Linux servers. It provides an easy-to-use interface and comprehensive security features, making it a popular choice among system administrators.&lt;/p&gt;

&lt;p&gt;CSF is not only a firewall but also an intrusion detection system, actively monitoring and blocking malicious activity.&lt;/p&gt;

&lt;p&gt;You can learn more about CSF and its features on their official website: &lt;a href="https://configserver.com/cp/csf.html" rel="noopener noreferrer"&gt;ConfigServer Security &amp;amp; Firewall&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why Choose CSF?
&lt;/h2&gt;

&lt;p&gt;There are several reasons to choose CSF over other firewall solutions for your Linux server:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Easy installation and setup&lt;/li&gt;
&lt;li&gt;Regular updates and active community support&lt;/li&gt;
&lt;li&gt;Compatibility with most Linux distributions and control panels&lt;/li&gt;
&lt;li&gt;Comprehensive security features, including intrusion detection and login failure tracking&lt;/li&gt;
&lt;li&gt;Customizable configuration options&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  How to Install and Configure CSF
&lt;/h2&gt;

&lt;p&gt;Before installing CSF, it's essential to uninstall or disable any other firewalls on your server. Follow these steps to install and configure CSF:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Log into your server as the root user via SSH.&lt;/li&gt;
&lt;li&gt;Download the latest version of CSF using the command:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;wget https://download.configserver.com/csf.tgz
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;Extract the downloaded archive:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;tar&lt;/span&gt; &lt;span class="nt"&gt;-xzf&lt;/span&gt; csf.tgz
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;Navigate to the extracted directory and run the installer script:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;cd &lt;/span&gt;csf
sh install.sh
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;Open the configuration file at &lt;code&gt;/etc/csf/csf.conf&lt;/code&gt; with your favorite text editor (e.g., nano or vim). Customize the settings to suit your security requirements.&lt;/li&gt;
&lt;li&gt;After configuring CSF, test your server's compatibility by running:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;perl /usr/local/csf/bin/csftest.pl
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;If the test is successful, enable CSF by changing the TESTING setting in the configuration file to 0.&lt;/li&gt;
&lt;li&gt;Restart CSF to apply the changes:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;csf &lt;span class="nt"&gt;-r&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;For more detailed instructions and configuration options, refer to the &lt;a href="https://configserver.com/cp/csf.html" rel="noopener noreferrer"&gt;official CSF documentation&lt;/a&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  Optimal CSF Configuration for Enhanced Security
&lt;/h3&gt;

&lt;p&gt;Here are some recommended settings for an optimal CSF configuration to enhance your Linux server's security.&lt;/p&gt;

&lt;p&gt;Keep in mind that these settings might not be suitable for every server environment, so it's important to tailor them according to your specific needs. Always test any changes before implementing them on a production server.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Restrict Incoming and Outgoing Connections&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Limit incoming and outgoing connections to only the necessary ports by specifying them in the &lt;code&gt;TCP_IN&lt;/code&gt;, &lt;code&gt;TCP_OUT&lt;/code&gt;, &lt;code&gt;UDP_IN&lt;/code&gt;, and &lt;code&gt;UDP_OUT&lt;/code&gt; sections. For example:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;TCP_IN &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"22,80,443"&lt;/span&gt;
TCP_OUT &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"22,80,443,53"&lt;/span&gt;
UDP_IN &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"53"&lt;/span&gt;
UDP_OUT &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"53"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;Enable Login Failure Detection&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Ensure that CSF tracks login failures by enabling the &lt;code&gt;LF_*&lt;/code&gt; options in the configuration file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;LF_TRIGGER &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"5"&lt;/span&gt;
LF_SSHD &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"5"&lt;/span&gt;
LF_FTPD &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"10"&lt;/span&gt;
LF_SMTPAUTH &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"5"&lt;/span&gt;
LF_POP3D &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"10"&lt;/span&gt;
LF_IMAPD &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"10"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This example sets a trigger for a temporary block after 5 failed login attempts within the specified time period for SSH, FTP, SMTP, POP3, and IMAP.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Enable Process Tracking&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Monitor server processes for suspicious activity by enabling process tracking:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;PT_LIMIT &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"60"&lt;/span&gt;
PT_USERMEM &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"200"&lt;/span&gt;
PT_USERTIME &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"1800"&lt;/span&gt;
PT_USERKILL &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"1"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This example sets a 60-second interval for process tracking, with a memory usage limit of 200 MB, a maximum process time of 1800 seconds, and the ability to kill processes that exceed these limits.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Remember to restart CSF after making any changes to the configuration file:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;csf &lt;span class="nt"&gt;-r&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Using Profiles in CSF for Enhanced Security
&lt;/h2&gt;

&lt;p&gt;Profiles in CSF are predefined sets of configuration options tailored to specific use cases or security levels. They allow you to quickly switch between different configurations without manually adjusting individual settings.&lt;/p&gt;

&lt;p&gt;This can be especially useful when you want to enforce stricter security measures or relax the rules temporarily. In this section, we'll explain what profiles are, how to use them, and some considerations when implementing them.&lt;/p&gt;

&lt;h3&gt;
  
  
  What are CSF Profiles?
&lt;/h3&gt;

&lt;p&gt;CSF profiles are essentially configuration files that store specific settings for different scenarios. These profiles can be applied with a single command, making it easy to switch between various security configurations.&lt;/p&gt;

&lt;p&gt;CSF comes with several default profiles, each designed for a particular purpose, such as a web server or a mail server.&lt;/p&gt;

&lt;h3&gt;
  
  
  How to Use CSF Profiles
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;First, navigate to the CSF profile directory:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;cd&lt;/span&gt; /usr/local/csf/profiles
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;List available profiles:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;ls&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You should see a list of default profiles, such as &lt;code&gt;webserver.conf&lt;/code&gt;, &lt;code&gt;mailserver.conf&lt;/code&gt;, and &lt;code&gt;default.conf&lt;/code&gt;.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;To apply a profile, use the following command:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;csf &lt;span class="nt"&gt;--profile&lt;/span&gt; &amp;lt;profile_name&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;For example, to apply the &lt;code&gt;webserver.conf&lt;/code&gt; profile, use:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;csf &lt;span class="nt"&gt;--profile&lt;/span&gt; webserver
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;If you want to create your custom profile, copy the existing configuration file to the profiles directory:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;cp&lt;/span&gt; /etc/csf/csf.conf /usr/local/csf/profiles/my_custom_profile.conf
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then, edit the &lt;code&gt;my_custom_profile.conf&lt;/code&gt; file using your preferred text editor, and adjust the settings to suit your needs. Once you've made the changes, you can apply the custom profile using the same command mentioned earlier.&lt;/p&gt;

&lt;h3&gt;
  
  
  Considerations When Using CSF Profiles
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;Backup your current configuration before applying a new profile. This ensures that you can easily revert to the previous settings if needed.&lt;/li&gt;
&lt;li&gt;Test the new profile in a non-production environment before applying it to a live server. This helps identify any potential issues or conflicts that could arise.&lt;/li&gt;
&lt;li&gt;When creating custom profiles, ensure that you follow best practices for securing Linux servers, and consider your specific use case and environment.&lt;/li&gt;
&lt;li&gt;Regularly review and update your profiles to stay up-to-date with the latest security recommendations and best practices.&lt;/li&gt;
&lt;li&gt;Keep in mind that applying a new profile will overwrite the current settings. Make sure to double-check the contents of the profile before applying it, especially if you're using a custom profile or have made changes to the default profiles.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;By understanding and utilizing CSF profiles, you can efficiently manage and switch between different security configurations for your Linux server. This not only saves time but also ensures that your server stays protected under various circumstances.&lt;/p&gt;

&lt;h2&gt;
  
  
  Setting Up the CSF User Interface
&lt;/h2&gt;

&lt;p&gt;CSF provides a web-based user interface (UI) for managing and configuring the firewall. This graphical interface is particularly useful for those who are not comfortable working with command-line tools or prefer a visual way of managing settings.&lt;/p&gt;

&lt;p&gt;In this section, we'll walk you through setting up the CSF UI and discuss some considerations for using it.&lt;/p&gt;

&lt;h3&gt;
  
  
  How to Set Up the CSF UI
&lt;/h3&gt;

&lt;p&gt;The CSF UI is available by default for popular control panels such as cPanel, DirectAdmin, and Webmin. If you are using one of these control panels, the CSF UI should already be integrated into your panel.&lt;/p&gt;

&lt;p&gt;For other control panels or a server without a control panel, you can set up the CSF UI using the following steps:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Ensure that you have the required dependencies installed on your server:&lt;/li&gt;
&lt;/ol&gt;

&lt;ul&gt;
&lt;li&gt;Perl&lt;/li&gt;
&lt;li&gt;The LWP (libwww-perl) module&lt;/li&gt;
&lt;li&gt;The GD (libgd) module&lt;/li&gt;
&lt;li&gt;The GD::Graph module&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;You can install these dependencies using your package manager. For example, on Ubuntu:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo &lt;/span&gt;apt-get &lt;span class="nb"&gt;install &lt;/span&gt;perl libwww-perl libgd-dev libgd-perl libgd-graph-perl
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;Open the CSF configuration file at &lt;code&gt;/etc/csf/csf.conf&lt;/code&gt; with your favorite text editor (e.g., nano or vim).&lt;/li&gt;
&lt;li&gt;Locate the following settings and modify them as follows:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;UI &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"1"&lt;/span&gt;
UI_PORT &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"&amp;lt;your_desired_port&amp;gt;"&lt;/span&gt;
UI_USER &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"&amp;lt;your_username&amp;gt;"&lt;/span&gt;
UI_PASS &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"&amp;lt;your_password&amp;gt;"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Replace &lt;code&gt;&amp;lt;your_desired_port&amp;gt;&lt;/code&gt; with an unused port number (e.g., 8080), &lt;code&gt;&amp;lt;your_username&amp;gt;&lt;/code&gt; with a username of your choice, and &lt;code&gt;&amp;lt;your_password&amp;gt;&lt;/code&gt; with a strong, unique password.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Save and close the configuration file.&lt;/li&gt;
&lt;li&gt;Restart CSF to apply the changes:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;csf &lt;span class="nt"&gt;-r&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Access the CSF UI by navigating to &lt;code&gt;http://your_server_ip:&amp;lt;your_desired_port&amp;gt;&lt;/code&gt; in your web browser, and log in with the username and password you specified in the configuration file.&lt;/p&gt;

&lt;h3&gt;
  
  
  How to Set Up HTTPS for the CSF UI
&lt;/h3&gt;

&lt;p&gt;It's essential to secure the CSF UI with HTTPS to protect your login credentials and data transmission. Using HTTPS is highly recommended, especially when accessing the UI over the internet.&lt;/p&gt;

&lt;p&gt;In this section, I'll show you how to set up HTTPS for the CSF UI using Let's Encrypt, ACME, or Certbot, and where to place the generated certificates so CSF can read them.&lt;/p&gt;

&lt;h4&gt;
  
  
  HTTPS with Certbot
&lt;/h4&gt;

&lt;ol&gt;
&lt;li&gt;Ensure that you have Certbot installed on your server. You can follow the instructions for your specific distribution on the &lt;a href="https://certbot.eff.org/instructions" rel="noopener noreferrer"&gt;Certbot website&lt;/a&gt;.&lt;/li&gt;
&lt;li&gt;Generate a certificate for your domain using Certbot:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo &lt;/span&gt;certbot certonly &lt;span class="nt"&gt;--standalone&lt;/span&gt; &lt;span class="nt"&gt;-d&lt;/span&gt; example.com
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Replace &lt;code&gt;example.com&lt;/code&gt; with your domain. Make sure the domain points to your server's IP address.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;After generating the certificate, you will find the certificate files in the &lt;code&gt;/etc/letsencrypt/live/example.com/&lt;/code&gt; directory. The files you need are fullchain.pem (the certificate) and privkey.pem (the private key).&lt;/li&gt;
&lt;li&gt;Copy the certificate files to a location where CSF can read them:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo cp&lt;/span&gt; /etc/letsencrypt/live/example.com/fullchain.pem /etc/csf/ui/ssl/cert.pem
&lt;span class="nb"&gt;sudo cp&lt;/span&gt; /etc/letsencrypt/live/example.com/privkey.pem /etc/csf/ui/ssl/key.pem
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;Open the CSF configuration file at &lt;code&gt;/etc/csf/csf.conf&lt;/code&gt; with your favorite text editor (e.g., nano or vim).&lt;/li&gt;
&lt;li&gt;Modify the following settings:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;UI_SSL &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"1"&lt;/span&gt;
UI_CERT &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"/etc/csf/ui/ssl/cert.pem"&lt;/span&gt;
UI_KEY &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"/etc/csf/ui/ssl/key.pem"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;Save and close the configuration file.&lt;/li&gt;
&lt;li&gt;Restart CSF to apply the changes:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;csf &lt;span class="nt"&gt;-r&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now, you can access the CSF UI securely over HTTPS by navigating to &lt;code&gt;https://example.com:&amp;lt;your_desired_port&amp;gt;&lt;/code&gt; in your web browser.&lt;/p&gt;

&lt;p&gt;Remember to renew the Let's Encrypt certificate every 90 days, as they have a short validity period. You can automate this process using a cron job.&lt;/p&gt;

&lt;p&gt;Keep in mind that HTTPS is necessary and highly recommended for securing the CSF UI. By following these steps, you can ensure that your login credentials and data transmission remain safe from potential threats.&lt;/p&gt;

&lt;h3&gt;
  
  
  Considerations When Using the CSF UI
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;Choose a strong, unique password for the CSF UI to prevent unauthorized access. Make sure to update the password regularly and avoid using the same password for other services.&lt;/li&gt;
&lt;li&gt;Restrict access to the CSF UI by allowing only specific IP addresses to connect to the UI. You can do this by modifying the &lt;code&gt;UI_ALLOW&lt;/code&gt; setting in the CSF configuration file:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;UI_ALLOW &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"192.168.1.1,192.168.1.2"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Replace the example IP addresses with the ones you want to allow access to the CSF UI.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Ensure that the chosen port for the CSF UI is not already in use by other services. Additionally, it's recommended to choose a non-standard port to reduce the chances of automated attacks.&lt;/li&gt;
&lt;li&gt;Regularly update the CSF UI and its dependencies to protect against known vulnerabilities and security issues.&lt;/li&gt;
&lt;li&gt;Monitor access logs to identify any suspicious activity or unauthorized login attempts. CSF logs can be found at &lt;code&gt;/var/log/lfd.log&lt;/code&gt;.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;By setting up and using the CSF UI, you can efficiently manage and configure your firewall settings through an easy-to-use graphical interface.&lt;/p&gt;

&lt;p&gt;Make sure to follow best practices and consider the points mentioned above to maintain a secure and reliable environment.&lt;/p&gt;

&lt;h2&gt;
  
  
  CSF Protection Against DDoS Attacks
&lt;/h2&gt;

&lt;p&gt;CSF can help protect your server against Distributed Denial of Service (DDoS) attacks by implementing various configurations and security measures.&lt;/p&gt;

&lt;p&gt;In this section, I'll cover how CSF can defend against DDoS attacks and provide some example configurations and recommendations.&lt;/p&gt;

&lt;h3&gt;
  
  
  SYN Flood Protection
&lt;/h3&gt;

&lt;p&gt;SYN flood attacks are a type of DDoS attack where an attacker sends a large number of SYN packets to a server, causing it to exhaust its resources while trying to establish connections.&lt;/p&gt;

&lt;p&gt;To enable SYN flood protection in CSF, adjust the following settings in the &lt;code&gt;/etc/csf/csf.conf&lt;/code&gt; file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;SYNFLOOD &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"1"&lt;/span&gt;
SYNFLOOD_RATE &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"100/s"&lt;/span&gt;
SYNFLOOD_BURST &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"150"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;These settings will enable SYN flood protection and configure the rate and burst limits for incoming connections.&lt;/p&gt;

&lt;h3&gt;
  
  
  Connection Limit Protection
&lt;/h3&gt;

&lt;p&gt;By limiting the number of simultaneous connections to your server, you can mitigate DDoS attacks targeting specific services.&lt;/p&gt;

&lt;p&gt;To enable connection limit protection, configure the &lt;code&gt;CONNLIMIT&lt;/code&gt; setting:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;CONNLIMIT &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"22;5,80;50,443;50"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This example limits the number of connections to 5 for SSH (22), 50 for HTTP (80), and 50 for HTTPS (443).&lt;/p&gt;

&lt;h3&gt;
  
  
  Port Flood Protection
&lt;/h3&gt;

&lt;p&gt;Port flood protection helps defend against DDoS attacks that target specific ports on your server.&lt;/p&gt;

&lt;p&gt;To enable port flood protection, configure the &lt;code&gt;PORTFLOOD&lt;/code&gt; setting:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;PORTFLOOD &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"22;tcp;5;300,80;tcp;30;5,443;tcp;30;5"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This example limits the rate of new connections for SSH (22) to 5 per 300 seconds, and for HTTP (80) and HTTPS (443) to 30 per 5 seconds.&lt;/p&gt;

&lt;h3&gt;
  
  
  Blocklists
&lt;/h3&gt;

&lt;p&gt;CSF can integrate with various IP blocklists to prevent known malicious IP addresses from accessing your server.&lt;/p&gt;

&lt;p&gt;To enable blocklist integration, configure the &lt;code&gt;BLOCKLIST_*&lt;/code&gt; settings in the CSF configuration file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;BLOCKLIST_DE &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"1"&lt;/span&gt;
BLOCKLIST_6DE &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"1"&lt;/span&gt;
BLOCKLIST_DE_URL &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"https://lists.blocklist.de/lists/all.txt"&lt;/span&gt;
BLOCKLIST_6DE_URL &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"https://lists.blocklist.de/lists/ipv6/all.txt"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This example enables integration with the &lt;code&gt;blocklist.de&lt;/code&gt; blocklists for both IPv4 and IPv6 addresses.&lt;/p&gt;

&lt;h3&gt;
  
  
  Country-Level Blocking
&lt;/h3&gt;

&lt;p&gt;CSF allows you to block access from specific countries using the &lt;code&gt;CC_DENY&lt;/code&gt; and &lt;code&gt;CC_ALLOW_FILTER&lt;/code&gt; settings. While this method may not be suitable for all situations, it can be useful in cases where you want to restrict access from countries known for launching DDoS attacks.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;CC_DENY &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"CN,IR,RU"&lt;/span&gt;
CC_ALLOW_FILTER &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"US,CA,GB"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This example blocks access from China (CN), Iran (IR), and Russia (RU) and only allows incoming connections from the United States (US), Canada (CA), and the United Kingdom (GB).&lt;/p&gt;

&lt;p&gt;Remember to restart CSF after making any changes to the configuration file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;csf &lt;span class="nt"&gt;-r&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;By implementing these configurations and recommendations, you can significantly enhance your server's protection against DDoS attacks.&lt;/p&gt;

&lt;p&gt;Keep in mind that no security measure is foolproof, so it's crucial to regularly monitor your server for potential threats and adapt your CSF settings accordingly.&lt;/p&gt;

&lt;h2&gt;
  
  
  Alternative Security Solutions
&lt;/h2&gt;

&lt;p&gt;While CSF is an excellent choice for Linux server security, you might want to consider alternative solutions that offer similar features:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://wiki.ubuntu.com/UncomplicatedFirewall" rel="noopener noreferrer"&gt;UFW (Uncomplicated Firewall)&lt;/a&gt;: A user-friendly firewall for Ubuntu-based systems.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://firewalld.org/" rel="noopener noreferrer"&gt;Firewalld&lt;/a&gt;: A firewall management tool for Linux distributions that use systemd.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://www.netfilter.org/projects/iptables/index.html" rel="noopener noreferrer"&gt;IPTables&lt;/a&gt;: A powerful command-line tool for packet filtering and network address translation on Linux.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;Securing your Linux server is essential to protect your data and maintain your server's integrity. CSF provides a powerful and user-friendly solution to achieve this goal.&lt;/p&gt;

&lt;p&gt;By following the steps outlined in this article, you can easily install and configure CSF on your Linux server. Don't forget to explore alternative security solutions like UFW, Firewalld, and IPTables if you're looking for additional options.&lt;/p&gt;

&lt;p&gt;I hope you found this article helpful and informative in securing your Linux server with CSF. If you enjoyed this article and found it valuable, please feel free to share it with others who might benefit from it. I also encourage you to leave a comment with your thoughts or questions, and I'll be more than happy to help. 😊&lt;/p&gt;

&lt;p&gt;Stay vigilant and keep your servers secure in 2023 and beyond!&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;Related reading:&lt;/strong&gt; &lt;a href="https://mecanik.dev/en/posts/linux-server-hardening-guide-2026/" rel="noopener noreferrer"&gt;Linux Server Hardening Guide for 2026&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/server-security-audit-what-gets-checked/" rel="noopener noreferrer"&gt;Server Security Audit Checklist: What Actually Gets Checked&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/cloudflare-zero-trust-enterprise-access-security/" rel="noopener noreferrer"&gt;Cloudflare Zero Trust: Enterprise Access Security Guide&lt;/a&gt; and &lt;a href="https://mecanik.dev/en/posts/runtime-encrypted-strings-part-1/" rel="noopener noreferrer"&gt;Runtime encrypted strings: Part 1&lt;/a&gt;.&lt;/p&gt;

</description>
      <category>linux</category>
      <category>csf</category>
      <category>firewall</category>
      <category>networking</category>
    </item>
    <item>
      <title>Ecommerce Website Development: Shopify vs Custom</title>
      <dc:creator>Mecanik1337</dc:creator>
      <pubDate>Wed, 07 Oct 2026 06:00:00 +0000</pubDate>
      <link>https://dev.to/mecanik-dev/ecommerce-website-development-shopify-vs-custom-b30</link>
      <guid>https://dev.to/mecanik-dev/ecommerce-website-development-shopify-vs-custom-b30</guid>
      <description>&lt;p&gt;Ecommerce website development is one of the highest-stakes decisions an online retailer makes, because the platform you choose shapes your costs, your flexibility, and your ceiling for growth. In 2026 the core question for most UK businesses comes down to this: a hosted platform like Shopify, or a custom build. Both can run a successful store. They suit very different situations. This guide compares them honestly on cost, control, performance, scalability, and SEO, then gives a clear recommendation for each type of retailer.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;TL;DR&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Shopify is the right default for most small and mid-sized UK retailers: fast to launch, low maintenance, and reliable out of the box&lt;/li&gt;
&lt;li&gt;Custom ecommerce development wins when you have unusual requirements, complex integrations, or scale that platform fees and limits start to constrain&lt;/li&gt;
&lt;li&gt;WooCommerce sits in between: open-source flexibility on WordPress, but with more maintenance responsibility on you&lt;/li&gt;
&lt;li&gt;The biggest hidden costs of hosted platforms are transaction fees and app subscriptions, which add up as you grow&lt;/li&gt;
&lt;li&gt;Choose the platform around your actual requirements and growth plan, not around what is trendy&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  The Ecommerce Platform Landscape in 2026
&lt;/h2&gt;

&lt;p&gt;Ecommerce website development falls into three broad approaches. Hosted platforms like Shopify handle the infrastructure, security, and updates for you in exchange for a monthly fee and, often, transaction charges. Open-source platforms like WooCommerce give you the software for free but make you responsible for hosting and maintenance. Custom development builds the store, or parts of it, specifically for your business.&lt;/p&gt;

&lt;p&gt;None of these is universally best. A store selling 20 products has very different needs from one selling 20,000 with complex pricing rules and warehouse integrations. The right choice is the one that matches your requirements today and gives you room to grow without a painful rebuild.&lt;/p&gt;

&lt;h2&gt;
  
  
  Shopify: Strengths and Limits
&lt;/h2&gt;

&lt;p&gt;Shopify dominates UK ecommerce for good reasons. It is fast to set up, handles hosting and security for you, processes payments reliably, and has a vast ecosystem of themes and apps. For a retailer who wants to start selling quickly without managing technical infrastructure, it is hard to beat.&lt;/p&gt;

&lt;p&gt;The trade-offs appear as you scale. Shopify charges monthly subscription fees, and unless you use Shopify Payments, additional transaction fees on every sale. The app ecosystem that makes Shopify flexible also means recurring subscription costs, since many features you need are paid third-party apps. Deep customisation is constrained by what the platform allows; you work within Shopify's structure rather than around it.&lt;/p&gt;

&lt;p&gt;For most small and mid-sized retailers, those limits never bite. For high-volume stores or businesses with unusual workflows, they eventually do.&lt;/p&gt;

&lt;h2&gt;
  
  
  Custom Ecommerce Development: Strengths and Limits
&lt;/h2&gt;

&lt;p&gt;A custom ecommerce build means the store is developed specifically for your business, typically on a framework rather than a hosted platform. The advantage is total control. There are no platform limits on functionality, no per-transaction platform fees, and the design and checkout flow can be built exactly around how you sell.&lt;/p&gt;

&lt;p&gt;This control comes at a price. Custom development costs more upfront and takes longer to launch. You are responsible for hosting, security, and maintenance, which our &lt;a href="https://mecanik.dev/en/posts/website-security-audit-for-uk-businesses-in-2026/" rel="noopener noreferrer"&gt;website security audit guide&lt;/a&gt; covers in depth. And you need a capable development partner, because a custom store is only as good as the team behind it.&lt;/p&gt;

&lt;p&gt;Custom development pays off when your requirements genuinely exceed what platforms offer, or when your sales volume makes platform and transaction fees more expensive than running your own infrastructure.&lt;/p&gt;

&lt;h2&gt;
  
  
  Shopify vs WooCommerce vs Custom: Side by Side
&lt;/h2&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Criterion&lt;/th&gt;
&lt;th&gt;Shopify&lt;/th&gt;
&lt;th&gt;WooCommerce&lt;/th&gt;
&lt;th&gt;Custom build&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Setup speed&lt;/td&gt;
&lt;td&gt;Fast&lt;/td&gt;
&lt;td&gt;Moderate&lt;/td&gt;
&lt;td&gt;Slow&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Upfront cost&lt;/td&gt;
&lt;td&gt;Low&lt;/td&gt;
&lt;td&gt;Low to moderate&lt;/td&gt;
&lt;td&gt;High&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Monthly cost&lt;/td&gt;
&lt;td&gt;Subscription + fees&lt;/td&gt;
&lt;td&gt;Hosting + plugins&lt;/td&gt;
&lt;td&gt;Hosting only&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Customisation&lt;/td&gt;
&lt;td&gt;Limited to platform&lt;/td&gt;
&lt;td&gt;High&lt;/td&gt;
&lt;td&gt;Unlimited&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Maintenance burden&lt;/td&gt;
&lt;td&gt;Minimal (Shopify handles it)&lt;/td&gt;
&lt;td&gt;On you&lt;/td&gt;
&lt;td&gt;On you&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Scalability&lt;/td&gt;
&lt;td&gt;Good, within limits&lt;/td&gt;
&lt;td&gt;Good with effort&lt;/td&gt;
&lt;td&gt;Excellent&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Transaction fees&lt;/td&gt;
&lt;td&gt;Often yes&lt;/td&gt;
&lt;td&gt;No (just payment processor)&lt;/td&gt;
&lt;td&gt;No (just payment processor)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Best for&lt;/td&gt;
&lt;td&gt;Most SMEs&lt;/td&gt;
&lt;td&gt;WordPress-based retailers&lt;/td&gt;
&lt;td&gt;Complex or high-volume stores&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;h2&gt;
  
  
  Performance and SEO for Ecommerce
&lt;/h2&gt;

&lt;p&gt;For an online store, performance is revenue. Slow pages lose sales, and Google's Core Web Vitals make speed a ranking factor. This is one area where the platform choice has real consequences.&lt;/p&gt;

&lt;p&gt;Shopify delivers solid performance out of the box, though heavy use of third-party apps can slow a store down, since each app often adds scripts. WooCommerce performance depends heavily on your hosting and how the site is built; a poorly optimised WooCommerce store can be slow, while a well-built one is fast. Custom builds can achieve the best performance because nothing is included that you do not need, but only if performance is a deliberate priority during development.&lt;/p&gt;

&lt;p&gt;SEO follows similar logic. All three approaches can rank well, but custom and well-built WooCommerce stores give you the most control over technical SEO, URL structure, and page speed. Whichever route you take, image optimisation matters enormously for stores with large catalogues, which is why we cover techniques like &lt;a href="https://mecanik.dev/en/posts/cloudflare-image-resizing-for-wordpress/" rel="noopener noreferrer"&gt;Cloudflare image resizing for WordPress&lt;/a&gt; for WooCommerce-based shops.&lt;/p&gt;

&lt;h2&gt;
  
  
  Security and Payments
&lt;/h2&gt;

&lt;p&gt;Taking payments online means taking security seriously. Hosted platforms like Shopify handle PCI compliance and security updates for you, which removes a significant burden and risk. With WooCommerce or a custom build, that responsibility shifts to you and your development partner: keeping software patched, hardening the server, and ensuring the payment flow is secure.&lt;/p&gt;

&lt;p&gt;This is a genuine factor in the decision. If you do not have the resources or appetite to manage security properly, a hosted platform's built-in protection is worth a great deal. If you do, a custom or self-hosted store gives you more control over the entire payment experience.&lt;/p&gt;

&lt;h2&gt;
  
  
  When to Choose Shopify
&lt;/h2&gt;

&lt;p&gt;Choose Shopify if you want to launch quickly, sell a manageable catalogue, and avoid managing technical infrastructure. It suits most small and mid-sized UK retailers, especially those without an in-house technical team. The monthly and transaction fees are a fair trade for not having to run, secure, and maintain the platform yourself. If your store is your business but technology is not, Shopify is usually the pragmatic answer.&lt;/p&gt;

&lt;h2&gt;
  
  
  When to Choose a Custom Build
&lt;/h2&gt;

&lt;p&gt;Choose custom ecommerce development when your requirements outgrow what platforms allow. That includes complex pricing or subscription models, deep integrations with ERP or warehouse systems, very large catalogues, unusual checkout flows, or sales volumes high enough that platform and transaction fees become a meaningful cost. At that point, the upfront investment in a custom store is justified by the control, performance, and savings it delivers. Our guide on &lt;a href="https://mecanik.dev/en/posts/wordpress-vs-custom-web-development-what-uk-businesses-need-to-know/" rel="noopener noreferrer"&gt;WordPress versus custom web development&lt;/a&gt; explores this build-versus-buy decision more broadly.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Honest Recommendation for 2026
&lt;/h2&gt;

&lt;p&gt;Most UK retailers should start with Shopify or a well-built WooCommerce store, and only move to custom development when they have concrete evidence that platform limits are holding the business back. Starting custom because it sounds more serious usually means paying for flexibility you do not yet need and taking on maintenance you are not ready for.&lt;/p&gt;

&lt;p&gt;The reverse mistake also happens: staying on a hosted platform long after transaction fees, app subscriptions, and customisation limits have started costing real money. The right move is to match the platform to where the business actually is, and to revisit the decision as it grows.&lt;/p&gt;

&lt;h2&gt;
  
  
  Key Takeaways
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;Shopify is the pragmatic default for most UK retailers: fast, reliable, and low-maintenance, with fees that grow as you scale&lt;/li&gt;
&lt;li&gt;Custom ecommerce development offers unlimited control and no platform fees, at higher upfront cost and maintenance responsibility&lt;/li&gt;
&lt;li&gt;WooCommerce sits between the two: flexible and open-source, but you manage hosting and security&lt;/li&gt;
&lt;li&gt;Performance and SEO are achievable on all three, but custom and well-built stores give the most control&lt;/li&gt;
&lt;li&gt;Hosted platforms handle PCI compliance and security for you; self-hosted stores shift that responsibility to you&lt;/li&gt;
&lt;li&gt;Match the platform to your real requirements and growth plan, and revisit the decision as the business scales&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Related reading:&lt;/strong&gt; &lt;a href="https://mecanik.dev/en/posts/drupal-web-development-a-2026-guide/" rel="noopener noreferrer"&gt;Drupal Web Development - A 2026 Guide&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/how-much-does-a-website-cost-in-the-uk-in-2026/" rel="noopener noreferrer"&gt;How Much Does a Website Cost in the UK in 2026?&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/hire-wordpress-developer-rates-what-to-ask/" rel="noopener noreferrer"&gt;Hire a WordPress Developer: 2026 Rates and What to Ask&lt;/a&gt; and &lt;a href="https://mecanik.dev/en/posts/headless-cms-vs-traditional-cms/" rel="noopener noreferrer"&gt;Headless CMS vs. Traditional CMS: Which is Best in 2026?&lt;/a&gt;., &lt;a href="https://mecanik.dev/en/posts/woocommerce-performance-why-store-is-slow/" rel="noopener noreferrer"&gt;WooCommerce Performance: Why Your Store Is Slow&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  Frequently Asked Questions
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Is Shopify or a custom website better for ecommerce?&lt;/strong&gt;&lt;br&gt;
For most small and mid-sized UK retailers, Shopify is better because it is fast to launch and handles hosting, security, and maintenance. A custom build becomes better when you have complex requirements, deep integrations, or sales volumes where platform and transaction fees outweigh the cost of running your own store.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;How much does ecommerce website development cost in the UK?&lt;/strong&gt;&lt;br&gt;
A Shopify store with light customisation can cost a few thousand pounds plus monthly fees, while a custom ecommerce build typically ranges from £8,000 to £40,000 or more depending on complexity. Catalogue size, integrations, and design effort are the main cost drivers.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Is WooCommerce better than Shopify?&lt;/strong&gt;&lt;br&gt;
Neither is universally better. WooCommerce offers more flexibility and no platform transaction fees, but you manage hosting, security, and updates. Shopify is easier and lower-maintenance but charges subscription and often transaction fees. The right choice depends on your technical resources and customisation needs.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Does the ecommerce platform affect SEO?&lt;/strong&gt;&lt;br&gt;
Yes. All major platforms can rank well, but they differ in how much control you have over technical SEO, URL structure, and page speed. Custom and well-built WooCommerce stores generally offer the most SEO control, while Shopify provides a solid, lower-effort foundation.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Do I need a developer to build an ecommerce website?&lt;/strong&gt;&lt;br&gt;
Not always for a basic Shopify store, which you can set up yourself. But a developer adds significant value for custom design, performance optimisation, complex functionality, and any custom or WooCommerce build. The more your store needs to do, the more a capable development partner matters.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Are transaction fees a big deal on Shopify?&lt;/strong&gt;&lt;br&gt;
They can be as you scale. Shopify charges subscription fees, and additional transaction fees apply unless you use Shopify Payments. For a low-volume store these are minor, but for a high-volume retailer they add up, which is one reason large stores sometimes move to custom platforms.&lt;/p&gt;

</description>
      <category>ecommerce</category>
      <category>webdev</category>
      <category>shopify</category>
      <category>wordpress</category>
    </item>
    <item>
      <title>Learn Programming Fundamentals: Choosing the Right Language</title>
      <dc:creator>Mecanik1337</dc:creator>
      <pubDate>Tue, 06 Oct 2026 18:00:00 +0000</pubDate>
      <link>https://dev.to/mecanik-dev/learn-programming-fundamentals-choosing-the-right-language-34im</link>
      <guid>https://dev.to/mecanik-dev/learn-programming-fundamentals-choosing-the-right-language-34im</guid>
      <description>&lt;p&gt;Embarking on a journey into the world of programming can be both exciting and overwhelming. With countless programming languages to choose from, it's essential to pick the right one that aligns with your goals and aspirations.&lt;/p&gt;

&lt;p&gt;In this article, we will explore the factors to consider when choosing your first programming language and provide examples of code in popular languages to help illustrate the differences between them.&lt;/p&gt;

&lt;h2&gt;
  
  
  Factors to Consider When Choosing a Programming Language
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Career Goals&lt;/strong&gt;: If you plan to pursue a career in software development, it's essential to research which programming languages are in demand for the industries you're interested in.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Learning Curve&lt;/strong&gt;: Some languages have a steeper learning curve than others. For beginners, it's beneficial to start with a language that has a gentle learning curve and is easy to understand.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Community and Support&lt;/strong&gt;: A large, active community makes it easier to find solutions to common problems and learn best practices. Consider languages with extensive documentation and support resources.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Platform Compatibility&lt;/strong&gt;: Ensure the language you choose is compatible with the platforms you intend to target, such as web, mobile, or desktop applications.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Personal Preference&lt;/strong&gt;: Finally, your personal preferences and interests will play a role in your decision. Choose a language that you enjoy working with and feel motivated to learn.&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  Popular Programming Languages and Examples
&lt;/h2&gt;

&lt;p&gt;To give you a better idea of what different programming languages look like, let's examine a simple task: printing "Hello, World!" in several popular languages.&lt;/p&gt;

&lt;h3&gt;
  
  
  Python
&lt;/h3&gt;

&lt;p&gt;Python is known for its readability and ease of use, making it an excellent choice for beginners.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="nf"&gt;print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;Hello, World!&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Strengths&lt;/strong&gt;: Python is widely used in web development, data analysis, artificial intelligence, and automation. Its clear syntax and extensive library support make it a versatile and popular language among developers.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Use Cases&lt;/strong&gt;: Web applications (Django, Flask), data analysis (Pandas, NumPy), machine learning (TensorFlow, scikit-learn), automation scripting.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  JavaScript
&lt;/h3&gt;

&lt;p&gt;JavaScript is the primary language for web development and is essential for creating interactive web pages.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Hello, World!&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Strengths&lt;/strong&gt;: JavaScript is executed in the browser, allowing for dynamic, responsive websites. With the rise of Node.js, JavaScript has also expanded to server-side development, increasing its versatility.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Use Cases&lt;/strong&gt;: Front-end web development (React, Angular, Vue), back-end web development (Node.js, Express), mobile app development (React Native, Ionic).&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Java
&lt;/h3&gt;

&lt;p&gt;Java is a versatile language widely used in enterprise applications, Android app development, and web applications.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight java"&gt;&lt;code&gt;&lt;span class="kd"&gt;public&lt;/span&gt; &lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;HelloWorld&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
&lt;span class="kd"&gt;public&lt;/span&gt; &lt;span class="kd"&gt;static&lt;/span&gt; &lt;span class="kt"&gt;void&lt;/span&gt; &lt;span class="nf"&gt;main&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;String&lt;/span&gt;&lt;span class="o"&gt;[]&lt;/span&gt; &lt;span class="n"&gt;args&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
&lt;span class="nc"&gt;System&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;out&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;println&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Hello, World!"&lt;/span&gt;&lt;span class="o"&gt;);&lt;/span&gt;
&lt;span class="o"&gt;}&lt;/span&gt;
&lt;span class="o"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Strengths&lt;/strong&gt;: Java is platform-independent, meaning it can run on any device with a Java Virtual Machine (JVM). Its strong object-oriented programming (OOP) support and extensive libraries make it suitable for large-scale applications.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Use Cases&lt;/strong&gt;: Android app development, web applications (Spring, JavaServer Faces), enterprise applications, desktop applications.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Ruby
&lt;/h3&gt;

&lt;p&gt;Ruby is another beginner-friendly language, popular for web development with the Ruby on Rails framework.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight java"&gt;&lt;code&gt;&lt;span class="n"&gt;puts&lt;/span&gt; &lt;span class="s"&gt;"Hello, World!"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Strengths&lt;/strong&gt;: Ruby boasts an elegant, readable syntax and a strong focus on simplicity and productivity. The Ruby on Rails framework has made it popular for rapid web development.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Use Cases&lt;/strong&gt;: Web applications (Ruby on Rails, Sinatra), scripting, and automation.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  C++
&lt;/h3&gt;

&lt;p&gt;C++ is a powerful language with a steeper learning curve, often used in system programming, game development, and performance-critical applications.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight java"&gt;&lt;code&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="n"&gt;include&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="n"&gt;iostream&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;

&lt;span class="kt"&gt;int&lt;/span&gt; &lt;span class="nf"&gt;main&lt;/span&gt;&lt;span class="o"&gt;()&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
&lt;span class="nl"&gt;std:&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;&lt;span class="n"&gt;cout&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&amp;lt;&lt;/span&gt; &lt;span class="s"&gt;"Hello, World!"&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&amp;lt;&lt;/span&gt; &lt;span class="nl"&gt;std:&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;&lt;span class="n"&gt;endl&lt;/span&gt;&lt;span class="o"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="o"&gt;;&lt;/span&gt;
&lt;span class="o"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Strengths&lt;/strong&gt;: C++ offers low-level memory manipulation and excellent performance, making it suitable for performance-critical applications. It is also an extension of the C language, offering object-oriented programming features.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Use Cases&lt;/strong&gt;: System programming, game development (Unreal Engine), embedded systems, high-performance applications.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Swift
&lt;/h3&gt;

&lt;p&gt;Swift is Apple's programming language, designed for developing iOS and macOS applications. If you're interested in creating apps for the Apple ecosystem, Swift should be your go-to language.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight swift"&gt;&lt;code&gt;&lt;span class="nf"&gt;print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Hello, World!"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Strengths&lt;/strong&gt;: Swift offers modern, concise syntax, and strong performance. It is designed to be safe, fast, and easy to read, making it popular among developers building apps for Apple devices.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Use Cases&lt;/strong&gt;: iOS app development, macOS app development, server-side development (Vapor, Kitura).&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Kotlin
&lt;/h3&gt;

&lt;p&gt;Kotlin is a modern language that runs on the Java Virtual Machine (JVM). It has gained popularity for Android app development as an alternative to Java, offering more concise and expressive syntax.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight kotlin"&gt;&lt;code&gt;&lt;span class="k"&gt;fun&lt;/span&gt; &lt;span class="nf"&gt;main&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="nf"&gt;println&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Hello, World!"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Strengths&lt;/strong&gt;: Kotlin is interoperable with Java, allowing developers to use both languages in a project. It offers concise, expressive syntax and several modern language features, making it more enjoyable to work with than Java for many developers.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Use Cases&lt;/strong&gt;: Android app development, web applications (Ktor, Spring Boot), desktop applications, server-side development.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Go (Golang)
&lt;/h3&gt;

&lt;p&gt;Go, also known as Golang, is an open-source programming language developed by Google. It's designed for efficient, high-performance software and is particularly suitable for concurrent programming and networked applications.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;package&lt;/span&gt; &lt;span class="n"&gt;main&lt;/span&gt;

&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="s"&gt;"fmt"&lt;/span&gt;

&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;main&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Println&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Hello, World!"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Strengths&lt;/strong&gt;: Go is known for its simplicity, strong performance, and efficient concurrency handling. It is designed for modern software development and excels in networked and distributed systems.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Use Cases&lt;/strong&gt;: Microservices, web servers, networking tools, distributed systems, containerization (Docker).&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  C# (C Sharp)
&lt;/h3&gt;

&lt;p&gt;C# is a versatile language developed by Microsoft, often used in the development of Windows applications, web services, and games (using the Unity game engine).&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight csharp"&gt;&lt;code&gt;&lt;span class="k"&gt;using&lt;/span&gt; &lt;span class="nn"&gt;System&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;HelloWorld&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="k"&gt;static&lt;/span&gt; &lt;span class="k"&gt;void&lt;/span&gt; &lt;span class="nf"&gt;Main&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="n"&gt;Console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;WriteLine&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Hello, World!"&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Strengths&lt;/strong&gt;: C# is a powerful, statically-typed language with strong support for object-oriented programming. It is tightly integrated with the .NET framework, making it ideal for Windows applications and services.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Use Cases&lt;/strong&gt;: Windows applications, web applications (ASP.NET), game development (Unity), and cross-platform mobile app development (Xamarin).&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Comparing Popular Programming Languages: Strengths, Weaknesses, and Ease of Learning
&lt;/h2&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Language&lt;/th&gt;
&lt;th&gt;Strengths&lt;/th&gt;
&lt;th&gt;Weaknesses&lt;/th&gt;
&lt;th&gt;Ease of Learning&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Python&lt;/td&gt;
&lt;td&gt;Readable syntax, versatile, extensive libraries&lt;/td&gt;
&lt;td&gt;Slower performance, limited mobile app development&lt;/td&gt;
&lt;td&gt;Easy&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;JavaScript&lt;/td&gt;
&lt;td&gt;Web development, dynamic websites, server-side (Node.js)&lt;/td&gt;
&lt;td&gt;Weakly typed, security concerns&lt;/td&gt;
&lt;td&gt;Easy&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Java&lt;/td&gt;
&lt;td&gt;Platform-independent, strong OOP support, versatile&lt;/td&gt;
&lt;td&gt;Verbose syntax, slower than C++&lt;/td&gt;
&lt;td&gt;Moderate&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Ruby&lt;/td&gt;
&lt;td&gt;Elegant syntax, rapid web development (Ruby on Rails)&lt;/td&gt;
&lt;td&gt;Slower performance, less popular than Python, JS&lt;/td&gt;
&lt;td&gt;Easy&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;C++&lt;/td&gt;
&lt;td&gt;Low-level memory manipulation, high performance&lt;/td&gt;
&lt;td&gt;Steeper learning curve, complex syntax&lt;/td&gt;
&lt;td&gt;Difficult&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Swift&lt;/td&gt;
&lt;td&gt;Modern syntax, Apple ecosystem, strong performance&lt;/td&gt;
&lt;td&gt;Limited to Apple platforms&lt;/td&gt;
&lt;td&gt;Moderate&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Kotlin&lt;/td&gt;
&lt;td&gt;Java interoperability, modern features, concise syntax&lt;/td&gt;
&lt;td&gt;Smaller community, less mature than Java&lt;/td&gt;
&lt;td&gt;Moderate&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Go (Golang)&lt;/td&gt;
&lt;td&gt;Simple syntax, high performance, efficient concurrency&lt;/td&gt;
&lt;td&gt;Limited use cases, less mature than alternatives&lt;/td&gt;
&lt;td&gt;Moderate&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;C#&lt;/td&gt;
&lt;td&gt;Powerful, .NET integration, versatile&lt;/td&gt;
&lt;td&gt;Limited cross-platform support, tied to Microsoft&lt;/td&gt;
&lt;td&gt;Moderate&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;h2&gt;
  
  
  Tips for Learning Your Chosen Programming Language
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Practice Regularly&lt;/strong&gt;: Consistent practice is key to becoming proficient in any programming language. Set aside time each day or week to work on coding exercises and projects.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Start Small&lt;/strong&gt;: Break down complex tasks into smaller, manageable parts. Build simple projects and gradually work your way up to more challenging ones as your skills develop.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Ask for Help&lt;/strong&gt;: Don't be afraid to ask questions or seek help from others. Join programming forums, communities, or social media groups to connect with experienced developers and fellow learners.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Read Code&lt;/strong&gt;: Reading code written by others can help you learn new techniques, best practices, and understand different programming styles.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Stay Curious&lt;/strong&gt;: Keep exploring new concepts, libraries, and tools. This will not only enhance your skills but also help you stay engaged and motivated in your learning journey.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Remember that patience, persistence, and a passion for learning are essential for mastering any programming language.&lt;/p&gt;

&lt;h2&gt;
  
  
  Resources for Learning and Practicing Programming
&lt;/h2&gt;

&lt;p&gt;Below is a list of resources where users can learn more and practice code development:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://www.codecademy.com/" rel="noopener noreferrer"&gt;Codecademy&lt;/a&gt; - An interactive platform that offers hands-on coding courses in various programming languages.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://www.freecodecamp.org/" rel="noopener noreferrer"&gt;freeCodeCamp&lt;/a&gt; - A non-profit organization that provides a comprehensive curriculum and hands-on projects to learn web development.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://www.coursera.org/" rel="noopener noreferrer"&gt;Coursera&lt;/a&gt; - A platform that offers a wide range of programming courses and specializations from top universities and institutions.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://www.edx.org/" rel="noopener noreferrer"&gt;edX&lt;/a&gt; - Another platform offering programming courses from top universities, covering various languages and development techniques.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://leetcode.com/" rel="noopener noreferrer"&gt;LeetCode&lt;/a&gt; - A platform for practicing coding problems, focusing on data structures and algorithms, to help users prepare for technical interviews.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://www.hackerrank.com/" rel="noopener noreferrer"&gt;HackerRank&lt;/a&gt; - A website that offers coding challenges and competitions in various domains, including algorithms, artificial intelligence, and databases.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://www.codewars.com/" rel="noopener noreferrer"&gt;Codewars&lt;/a&gt; - A community-driven platform where users can improve their programming skills by solving coding challenges known as "kata."&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://developer.mozilla.org/en-US/" rel="noopener noreferrer"&gt;MDN Web Docs&lt;/a&gt; - A comprehensive resource for web developers, offering tutorials, guides, and reference materials for HTML, CSS, and JavaScript.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://www.w3schools.com/" rel="noopener noreferrer"&gt;W3Schools&lt;/a&gt; - A popular web development tutorial site, covering a wide range of topics like HTML, CSS, JavaScript, Python, and more.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;These resources offer valuable learning materials, hands-on practice opportunities, and supportive communities to help users improve their programming skills and build confidence in their abilities.&lt;/p&gt;

&lt;h2&gt;
  
  
  Making Your Decision
&lt;/h2&gt;

&lt;p&gt;By considering your career goals, learning curve, community support, platform compatibility, and personal preferences, you'll be better equipped to choose the right programming language for your needs. Additionally, the code examples provided should help illustrate the differences between these popular languages.&lt;/p&gt;

&lt;p&gt;Remember, there's no one-size-fits-all answer, and many developers eventually learn multiple languages throughout their careers. The most important thing is to start learning and never stop growing your skills.&lt;/p&gt;

&lt;p&gt;Good luck on your programming journey! 😀&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;Related reading:&lt;/strong&gt; &lt;a href="https://mecanik.dev/en/posts/what-is-software-development-a-2026-guide/" rel="noopener noreferrer"&gt;What Is Software Development? A 2026 UK Guide&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/runtime-encrypted-strings-part-1/" rel="noopener noreferrer"&gt;Runtime encrypted strings: Part 1&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/how-to-write-mini-dump-on-software-crash/" rel="noopener noreferrer"&gt;How to write Mini Dump on software crash&lt;/a&gt; and &lt;a href="https://mecanik.dev/en/posts/convert-dos-and-nt-paths-using-rtl-functions/" rel="noopener noreferrer"&gt;Convert DOS and NT paths using RTL functions&lt;/a&gt;., &lt;a href="https://mecanik.dev/en/posts/c-data-types-to-.net/" rel="noopener noreferrer"&gt;C++ data types to .NET&lt;/a&gt;&lt;/p&gt;

</description>
      <category>c</category>
      <category>cpp</category>
      <category>linux</category>
      <category>windows</category>
    </item>
    <item>
      <title>Runtime encrypted strings: Part 1</title>
      <dc:creator>Mecanik1337</dc:creator>
      <pubDate>Tue, 06 Oct 2026 06:00:00 +0000</pubDate>
      <link>https://dev.to/mecanik-dev/runtime-encrypted-strings-part-1-5f90</link>
      <guid>https://dev.to/mecanik-dev/runtime-encrypted-strings-part-1-5f90</guid>
      <description>&lt;h2&gt;
  
  
  Runtime Encrypted Strings
&lt;/h2&gt;

&lt;p&gt;Today we will go through the basics of runtime encrypted strings, why do we need to encrypt our strings and learn how to create our own.&lt;/p&gt;

&lt;p&gt;In this article you will understand and learn:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;What is runtime encryption and decryption&lt;/li&gt;
&lt;li&gt;Why do you need to encrypt your strings&lt;/li&gt;
&lt;li&gt;See how anybody can see your sensitive data&lt;/li&gt;
&lt;li&gt;Create your own custom encryption&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  What is runtime encryption and decryption
&lt;/h2&gt;

&lt;p&gt;This refers to data encrypted and/or decrypted during the runtime of a program (software, application). The data can be of any type from memory blocks, network traffic, strings, etc.&lt;/p&gt;

&lt;p&gt;One of the most common methods used for this purpose is obfuscation (basic). The other (advanced) mechanisms involve mutation/virtualization of compiled code.&lt;/p&gt;

&lt;p&gt;Today we will focus on a mechanism using &lt;a href="https://en.wikipedia.org/wiki/XOR_cipher" rel="noopener noreferrer"&gt;XOR obfuscation&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why encrypt strings?
&lt;/h2&gt;

&lt;p&gt;The moment you run your software everything is visible in memory. This applies to your end users as well which means they can see everything.&lt;/p&gt;

&lt;p&gt;One of the first things an attacker will do is look for strings inside your software. This will allow him to understand everything about your software with minimal effort.&lt;/p&gt;

&lt;p&gt;If you are storing sensitive data (like passwords or licenses) it is crucial to not keep them in plain text. Keeping them in plain text will make the life of an attacker easy.&lt;/p&gt;

&lt;p&gt;There is a number of ways people can use to analyze your software. The most known and common methods are static and runtime analysis.&lt;/p&gt;

&lt;p&gt;Let’s have a look at a simple example using a console app:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F32e0c730-c260-456e-fda2-195b1d04dc00%2F1200x675" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F32e0c730-c260-456e-fda2-195b1d04dc00%2F1200x675" width="834" height="452" alt="Sample non-encrypted 1"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;We compile this in Release mode (to avoid any debug information left inside). Let’s proceed and test the static and runtime analysis.&lt;/p&gt;

&lt;h3&gt;
  
  
  Static Analysis Test
&lt;/h3&gt;

&lt;p&gt;In static analysis the software does not need to execute. With that said, let’s open the sample in &lt;a href="https://ghidra-sre.org/" rel="noopener noreferrer"&gt;Ghidra&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;From the screenshot below you can see that the sample is compiled without any debug information:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2Fb16393bd-d60a-4613-5644-a7f28c9afc00%2F1200x675" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2Fb16393bd-d60a-4613-5644-a7f28c9afc00%2F1200x675" width="1200" height="650" alt="Sample non-encrypted 1-1"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;If we search for strings you can see that all our sensitive information is visible:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2Ff17e4ff8-60d4-4af9-ee3c-8e3ae949f300%2F1200x675" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2Ff17e4ff8-60d4-4af9-ee3c-8e3ae949f300%2F1200x675" width="1200" height="652" alt="Sample non-encrypted 1-2"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Once you highlighted the string you can open the decompiler view and see all the relevant code:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2Fcf6096ee-f879-4bd0-e3aa-7f796cb42a00%2F1200x675" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2Fcf6096ee-f879-4bd0-e3aa-7f796cb42a00%2F1200x675" width="1200" height="650" alt="Sample non-encrypted 1-3"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Pretty sad eh? 😕 Imagine you worked on your amazing software for months, and you are ready to sell it.&lt;/p&gt;

&lt;p&gt;I think the rest is self-explanatory, but I’m sure you get the point.&lt;/p&gt;

&lt;p&gt;What’s even sadder is the fact that this is so simple that even a 12-year old can do it. (and some actually do it)&lt;/p&gt;

&lt;h3&gt;
  
  
  Runtime Analysis Test
&lt;/h3&gt;

&lt;p&gt;In runtime analysis the software needs to run (execute). This means we need to use a software to open the process and read it (normally a debugger).&lt;/p&gt;

&lt;p&gt;However, a debugger is not really needed for this purpose. We can simply download a free tool like &lt;a href="https://processhacker.sourceforge.io/" rel="noopener noreferrer"&gt;Process Hacker&lt;/a&gt; and open the process:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F3ac98faa-2fd4-470c-9c56-53d0616fb600%2F1200x675" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F3ac98faa-2fd4-470c-9c56-53d0616fb600%2F1200x675" width="834" height="450" alt="Sample non-encrypted 2"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;That was rather simple right? And keep in mind that we haven’t even attached a debugger. A skilled and determined individual will use a debugger.&lt;/p&gt;

&lt;p&gt;When you attach a debugger you see much more, but that discussion is for another day.&lt;/p&gt;

&lt;h2&gt;
  
  
  Creating Runtime Encrypted Strings
&lt;/h2&gt;

&lt;p&gt;There are numerous ways you achieve this:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Using a third party software like &lt;a href="https://vmpsoft.com/" rel="noopener noreferrer"&gt;VMProtect&lt;/a&gt;, &lt;a href="https://www.oreans.com/Themida.php" rel="noopener noreferrer"&gt;Themida&lt;/a&gt;.&lt;/li&gt;
&lt;li&gt;Compile time string encryption like &lt;a href="https://github.com/JustasMasiulis/xorstr" rel="noopener noreferrer"&gt;xorstr&lt;/a&gt;.&lt;/li&gt;
&lt;li&gt;Using custom methods&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The first 2 options might not suit your needs. There are many ups and downs for each of them, which we will not discuss at this point.&lt;/p&gt;

&lt;p&gt;One thing you need to understand is that popularity means risk. When you use stuff found randomly on Google, someone already knows about it.&lt;/p&gt;

&lt;p&gt;Most people developed a tool against your tool. It’s just the way things are. They do it for a challenge, or to steal your work, but they do it.&lt;/p&gt;

&lt;p&gt;With this in mind, you must go custom. You can create your own string encryption from basic to advanced level.&lt;/p&gt;

&lt;h3&gt;
  
  
  The Plan
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Create an easy to use solution&lt;/li&gt;
&lt;li&gt;Keep strings encrypted at all times&lt;/li&gt;
&lt;li&gt;Decryption only when you need it&lt;/li&gt;
&lt;li&gt;Place the strings in random location (optional – not covered)&lt;/li&gt;
&lt;li&gt;Destroy the strings after using them (optional – not covered)&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  The Solution
&lt;/h3&gt;

&lt;p&gt;Start by defining our strings one by one as an array:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F9dc647fb-e92b-4fdd-9512-94489571d900%2F1200x675" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F9dc647fb-e92b-4fdd-9512-94489571d900%2F1200x675" width="834" height="225" alt="Step 1"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The array can hold an unlimited number of strings with a 256 length limit.&lt;/p&gt;

&lt;p&gt;I know this is a daunting task, especially if your strings are long. This is just for demonstration and later on we will create a more practical solution.&lt;/p&gt;

&lt;p&gt;The idea is to encrypt each character from the string. I will use a simple XOR encryption for this.&lt;/p&gt;

&lt;p&gt;Below you can see an example of how this would work:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F61f51e2b-a9a6-46e7-da6b-0fa703cccb00%2F1200x675" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F61f51e2b-a9a6-46e7-da6b-0fa703cccb00%2F1200x675" width="834" height="450" alt="Step 2"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The above has nothing complicated going on, it’s plain and simple yet quite powerful. You can use this inside a console application.&lt;/p&gt;

&lt;p&gt;After you compile and run, the result is unreadable bytes to the human eye:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2Fdf20fa22-7c05-4a93-8bca-da81d1fc1e00%2F1200x675" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2Fdf20fa22-7c05-4a93-8bca-da81d1fc1e00%2F1200x675" width="834" height="450" alt="Step 3"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;There you have it, your own little software to create runtime encrypted strings. 😏&lt;/p&gt;

&lt;h3&gt;
  
  
  The Result
&lt;/h3&gt;

&lt;p&gt;I’s time to put our solution into practice. Let’s create another sample for this purpose and add our code:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2Fca5b3dff-2934-4d1a-7ab9-f78348848200%2F1200x675" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2Fca5b3dff-2934-4d1a-7ab9-f78348848200%2F1200x675" width="834" height="646" alt="Step 4"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Notice 2 important things:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;I’ve left some strings in plain text so you can see the difference&lt;/li&gt;
&lt;li&gt;The decryption functions needs the length (more on this later)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;We compile the above in Release mode and run it. The new Sample is working normally:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F52e55e99-3f85-414c-5bb4-096b4b703c00%2F1200x675" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F52e55e99-3f85-414c-5bb4-096b4b703c00%2F1200x675" width="834" height="250" alt="Step 5"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;If we open the new Sample software in IDA (or Ghidra) the strings we encrypted are not visible:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2Fc86cee8d-7944-45d9-718c-cecc111d5a00%2F1200x675" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2Fc86cee8d-7944-45d9-718c-cecc111d5a00%2F1200x675" width="834" height="450" alt="Step 6"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I’ve mentioned that there are some string intentionally left plain in this sample. The reason why is, so we can follow them to see the code:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F01ab1fdd-f28e-4553-4838-aea18eb36d00%2F1200x675" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F01ab1fdd-f28e-4553-4838-aea18eb36d00%2F1200x675" width="710" height="675" alt="Step 7"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I had to scroll down to reach the text in the above image. You can see how different the compiled code is.&lt;/p&gt;

&lt;p&gt;We solved the static analysis problem, let’s move on to runtime.&lt;/p&gt;

&lt;p&gt;Open it in Process Hacker:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F48adaff6-5972-42af-2571-aed2e91d7600%2F1200x675" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fmecanik.dev%2Fcdn-cgi%2Fimagedelivery%2FxqiSCiPBXNEeBkfBRiRspQ%2F48adaff6-5972-42af-2571-aed2e91d7600%2F1200x675" width="834" height="450" alt="Step 8"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Voila! We solved the runtime analysis problem as well 😎&lt;/p&gt;

&lt;h2&gt;
  
  
  More on encrypted strings
&lt;/h2&gt;

&lt;p&gt;The above example is not very practical. Defining each string manually is a daunting task, as well as specifying the length of the string each time.&lt;/p&gt;

&lt;p&gt;Ideally we would need the following:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Reading a text file for strings&lt;/li&gt;
&lt;li&gt;Writing to a text file the resulted strings&lt;/li&gt;
&lt;li&gt;Adding the &lt;a href="https://en.cppreference.com/w/cpp/language/escape" rel="noopener noreferrer"&gt;Escape sequences&lt;/a&gt; to strings to avoid specifying the length each time.&lt;/li&gt;
&lt;li&gt;Add more complex XOR or any other method (optional)&lt;/li&gt;
&lt;li&gt;Place the strings on random locations (optional)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;I have prepared a nice solution for you to play with. You can test everything written in this article and also have your own ready to use tool to make runtime encrypted strings.&lt;/p&gt;

&lt;p&gt;It includes 4 projects:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;RuntimeStringEcryptor&lt;/strong&gt; which reads from a text file strings, encrypts them and then writes them to another text file.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Sample&lt;/strong&gt; is the plain simple console used to demonstrate with IDA.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;SampleEncryptedStrings&lt;/strong&gt; is the simple console with encrypted strings to demonstrate with IDA.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;SimpleRuntimeStringEncryption&lt;/strong&gt; is the initial playground where you can test this method.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Notes:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;If you don’t add escape sequence, the decryption will not know when to “stop”. The result being in gibberish/null data until it reaches the defined array size.&lt;/li&gt;
&lt;li&gt;Make sure you change the XOR keys I have used in my example.&lt;/li&gt;
&lt;li&gt;Avoid using the same words multiple times. They will generate the same bytes and it’s a risk of being detected.&lt;/li&gt;
&lt;/ul&gt;




&lt;p&gt;&lt;strong&gt;Related reading:&lt;/strong&gt; &lt;a href="https://mecanik.dev/en/posts/convert-dos-and-nt-paths-using-rtl-functions/" rel="noopener noreferrer"&gt;Convert DOS and NT paths using RTL functions&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/how-to-write-mini-dump-on-software-crash/" rel="noopener noreferrer"&gt;How to write Mini Dump on software crash&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/learn-programming-fundamentals-choosing-the-right-language/" rel="noopener noreferrer"&gt;Learn Programming Fundamentals: Choosing the Right Language&lt;/a&gt; and &lt;a href="https://mecanik.dev/en/posts/hire-cpp-developer-rates-specialisms-vetting/" rel="noopener noreferrer"&gt;Hire a C++ Developer: Rates, Specialisms and Vetting&lt;/a&gt;.&lt;/p&gt;

</description>
      <category>c</category>
      <category>cpp</category>
      <category>linux</category>
      <category>windows</category>
    </item>
    <item>
      <title>DeepSeek R1 vs. OpenAI o3-mini: Which API is Best?</title>
      <dc:creator>Mecanik1337</dc:creator>
      <pubDate>Mon, 05 Oct 2026 18:00:00 +0000</pubDate>
      <link>https://dev.to/mecanik-dev/deepseek-r1-vs-openai-o3-mini-which-api-is-best-2nm1</link>
      <guid>https://dev.to/mecanik-dev/deepseek-r1-vs-openai-o3-mini-which-api-is-best-2nm1</guid>
      <description>&lt;p&gt;Choosing between DeepSeek R1 vs OpenAI o3-mini is a critical decision for developers integrating reasoning APIs into software applications in 2026. When it comes to reasoning APIs, these are the two strongest candidates most teams end up weighing. Both models excel at complex tasks, code generation, mathematical analysis, and structured logic. However, they operate on different pricing structures, reasoning token methods, latency patterns, and structured data validation limits. This guide compares the two in detail to help you choose the best API for your developer workflows.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;TL;DR&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Understand reasoning models&lt;/strong&gt;; reasoning models utilise "thinking tokens" to solve problems before returning a response, improving accuracy on logical tasks.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;DeepSeek R1 is highly cost-effective&lt;/strong&gt;; R1 offers open-source weights and extremely low API costs, making it ideal for high-volume execution.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;OpenAI o3-mini delivers lower latency&lt;/strong&gt;; o3-mini excels at rapid, real-time responses and features robust structured JSON-schema support.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Evaluate data portability&lt;/strong&gt;; R1 can be hosted on your own cloud infrastructure, preventing vendor lock-in, while o3-mini is hosted exclusively on OpenAI.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Select based on task requirements&lt;/strong&gt;; use o3-mini for interactive, real-time web applications, and R1 for bulk analytical workflows and offline data processing.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  The Core Concept of Reasoning Models
&lt;/h2&gt;

&lt;p&gt;Unlike standard chat completion models, reasoning models are trained to think step by step before outputting answers.&lt;/p&gt;

&lt;p&gt;This reasoning process utilises specialised "thinking tokens." The model generates internal steps to cross-examine its assumptions, debug code, and analyse syntax. While this process improves the quality of responses on complex logical tasks, it increases response latency and token costs. Understanding how to manage these context sizes is essential for budgeting. To see how standard APIs differ from reasoning ones, read our guide on &lt;a href="https://mecanik.dev/en/posts/building-an-ai-chatbot-with-the-openai-api/" rel="noopener noreferrer"&gt;building an OpenAI API chatbot&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Latency vs. Reasoning Depth
&lt;/h2&gt;

&lt;p&gt;In production, latency is a critical consideration. If your application requires real-time user interaction, slow API responses will harm the user experience.&lt;/p&gt;

&lt;p&gt;OpenAI's o3-mini is optimised for speed. It returns complex reasoning answers in a fraction of the time required by larger models, making it ideal for interactive coding tools. In a head-to-head speed test, o3-mini comes out faster, while DeepSeek R1 prioritises reasoning depth. It writes longer internal reasoning steps, which can result in longer response times. To inspect how to handle edge compute limits and latency, read our comparison of &lt;a href="https://mecanik.dev/en/posts/cloudflare-workers-vs-aws-lambda-2026/" rel="noopener noreferrer"&gt;Cloudflare Workers vs AWS Lambda&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Structured Outputs and JSON Parsing
&lt;/h2&gt;

&lt;p&gt;When integrating AI into software workflows, receiving unstructured text is problematic. You must ensure the model returns structured data, such as JSON schemas, to integrate with your database.&lt;/p&gt;

&lt;p&gt;OpenAI o3-mini supports structured outputs with strict JSON schemas. This feature guarantees that the API response matches your specified JSON schema exactly, eliminating parsing errors. DeepSeek R1 also supports JSON formats, but developers must write clear system instructions and handle validation checks manually. If you are building database integrations, we suggest linking these APIs to edge databases; see &lt;a href="https://mecanik.dev/en/posts/cloudflare-d1-build-a-serverless-sql-database-on-the-edge/" rel="noopener noreferrer"&gt;Cloudflare D1 serverless database setup&lt;/a&gt; for details.&lt;/p&gt;

&lt;h2&gt;
  
  
  Pricing and Cost Optimisation
&lt;/h2&gt;

&lt;p&gt;API usage costs are a primary consideration when scaling AI applications. The table below highlights the key pricing differences between the two APIs.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Model API&lt;/th&gt;
&lt;th&gt;Input Cost (per 1M tokens)&lt;/th&gt;
&lt;th&gt;Output Cost (per 1M tokens)&lt;/th&gt;
&lt;th&gt;Hosting Flexibility&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;OpenAI o3-mini&lt;/td&gt;
&lt;td&gt;Higher&lt;/td&gt;
&lt;td&gt;Moderate&lt;/td&gt;
&lt;td&gt;Hosted only (proprietary)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;DeepSeek R1&lt;/td&gt;
&lt;td&gt;Extremely Low&lt;/td&gt;
&lt;td&gt;Extremely Low&lt;/td&gt;
&lt;td&gt;Portable (open weights)&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;DeepSeek R1 is highly cost-effective, providing reasoning capabilities at a fraction of the cost of proprietary alternatives. Furthermore, since R1 weights are open, you can host the model on your own hardware or deploy it to edge runtimes; see our &lt;a href="https://mecanik.dev/en/posts/cloudflare-workers-ai-tutorial/" rel="noopener noreferrer"&gt;Cloudflare Workers AI tutorial&lt;/a&gt; to learn how to deploy models serverless.&lt;/p&gt;

&lt;h2&gt;
  
  
  How the Two Reasoning APIs Compare at a Glance
&lt;/h2&gt;

&lt;p&gt;The headline choice comes down to a handful of dimensions that actually affect an integration: how much context each model accepts, how it handles structured data, where it can run, and what a request costs. The table below summarises the practical differences. Treat the specific figures as illustrative snapshots. Published limits and rates for both APIs change frequently, so confirm the current numbers in each provider's documentation before you commit.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Dimension&lt;/th&gt;
&lt;th&gt;OpenAI o3-mini&lt;/th&gt;
&lt;th&gt;DeepSeek R1&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Context window (typical)&lt;/td&gt;
&lt;td&gt;~200K tokens&lt;/td&gt;
&lt;td&gt;~64K tokens&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Max output per request&lt;/td&gt;
&lt;td&gt;~100K tokens&lt;/td&gt;
&lt;td&gt;~8K–32K tokens&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Structured outputs&lt;/td&gt;
&lt;td&gt;Native strict JSON schema&lt;/td&gt;
&lt;td&gt;JSON via prompting + manual validation&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Reasoning-effort control&lt;/td&gt;
&lt;td&gt;Adjustable (low/medium/high)&lt;/td&gt;
&lt;td&gt;Fixed reasoning behaviour&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Hosting&lt;/td&gt;
&lt;td&gt;OpenAI cloud only&lt;/td&gt;
&lt;td&gt;Hosted API or self-hosted (open weights)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Relative latency&lt;/td&gt;
&lt;td&gt;Lower&lt;/td&gt;
&lt;td&gt;Higher (longer reasoning traces)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Relative token price&lt;/td&gt;
&lt;td&gt;Higher&lt;/td&gt;
&lt;td&gt;Substantially lower&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Best-fit workload&lt;/td&gt;
&lt;td&gt;Interactive, real-time tools&lt;/td&gt;
&lt;td&gt;High-volume, batch analysis&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Two rows deserve extra attention. o3-mini exposes a reasoning-effort setting, so you can dial thinking down for simple calls and up for hard ones, a direct lever on both latency and cost. R1's open weights, by contrast, mean the same model can run inside your own network, which matters for data-residency and compliance requirements that a hosted-only API cannot satisfy.&lt;/p&gt;

&lt;h2&gt;
  
  
  Working Out the Cost per 1,000 Calls
&lt;/h2&gt;

&lt;p&gt;Per-million-token rates are hard to reason about in isolation, so it helps to work a realistic scenario end to end. Imagine a classification service that enriches each support ticket: roughly &lt;strong&gt;800 input tokens&lt;/strong&gt; of prompt and context, and &lt;strong&gt;1,200 output tokens&lt;/strong&gt; per reply, of which perhaps 900 are internal thinking tokens and 300 the visible answer. Reasoning models bill those thinking tokens at the standard output rate, so they count in full.&lt;/p&gt;

&lt;p&gt;Using illustrative published rates (o3-mini around $1.10 input and $4.40 output per million tokens; R1 around $0.55 input and $2.19 output per million), the arithmetic works out as follows:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Step&lt;/th&gt;
&lt;th&gt;OpenAI o3-mini&lt;/th&gt;
&lt;th&gt;DeepSeek R1&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Input: 800 tokens&lt;/td&gt;
&lt;td&gt;$0.00088&lt;/td&gt;
&lt;td&gt;$0.00044&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Output: 1,200 tokens&lt;/td&gt;
&lt;td&gt;$0.00528&lt;/td&gt;
&lt;td&gt;$0.00263&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Cost per call&lt;/td&gt;
&lt;td&gt;~$0.0062&lt;/td&gt;
&lt;td&gt;~$0.0031&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Cost per 1,000 calls&lt;/td&gt;
&lt;td&gt;~$6.16&lt;/td&gt;
&lt;td&gt;~$3.07&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Cost at 1M calls/month&lt;/td&gt;
&lt;td&gt;~$6,160&lt;/td&gt;
&lt;td&gt;~$3,070&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;At this shape of workload the hosted R1 API lands at roughly half the running cost of o3-mini. The gap widens as output tokens grow, because reasoning-heavy prompts spend most of their budget on the more expensive output side. The lesson is to estimate output tokens, thinking included, rather than input, since that is where reasoning-model bills are won or lost. Capping maximum output tokens and lowering reasoning effort on easy calls are the two most effective controls.&lt;/p&gt;

&lt;p&gt;Self-hosting R1 changes the equation again: you swap per-token fees for GPU rental. A high-memory GPU instance capable of serving the full model tends to run into the low thousands of pounds per month, so self-hosting only beats the API once sustained throughput is high enough to keep that hardware busy. Below that break-even point, the managed API is cheaper and far less operational work.&lt;/p&gt;

&lt;h2&gt;
  
  
  Choosing by Workload, Not by Winner
&lt;/h2&gt;

&lt;p&gt;Neither model is universally "better"; the right pick follows the shape of the job.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Choose OpenAI o3-mini when&lt;/strong&gt; the interaction is user-facing and latency is visible: coding assistants, chat features, autocomplete, or anything where a person waits for the response. Its native strict JSON schema also makes it the safer choice when a malformed response would break a downstream system, such as a function-calling agent or a database write. The adjustable reasoning effort lets one integration serve both quick and hard queries without swapping models.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Choose DeepSeek R1 when&lt;/strong&gt; volume is high and latency is hidden: overnight batch jobs, document enrichment, bulk classification, dataset labelling, or offline analysis where throughput and unit cost matter more than a second or two of delay. It is also the pragmatic choice under strict data-governance rules, because the open weights let you keep every token inside infrastructure you control.&lt;/p&gt;

&lt;p&gt;Many production stacks end up using both: a fast hosted model on the interactive path and a cheaper, self-hostable model on the batch path, with a routing layer that sends each request to the model that fits. That hybrid pattern captures most of the cost saving without sacrificing the responsiveness users notice.&lt;/p&gt;

&lt;h2&gt;
  
  
  Total Cost of Ownership and Switching Costs
&lt;/h2&gt;

&lt;p&gt;Sticker price is only part of the total cost of ownership. Because both APIs speak a broadly OpenAI-compatible request format, moving a prompt from one to the other is usually a matter of changing the endpoint, key, and model name rather than rewriting application logic. That keeps switching costs low and is a strong argument for not hard-coding a single provider. The larger migration effort sits elsewhere: strict-schema features and reasoning-effort parameters are provider-specific, so any code that depends on them needs a fallback path when you move to a model that lacks them.&lt;/p&gt;

&lt;p&gt;Factor in the softer costs too. A hosted API adds no operational burden but exposes you to rate limits, pricing changes, and regional availability. Self-hosting removes those risks but adds GPU provisioning, scaling, patching, and monitoring, all real engineering time that belongs in the budget. Abstracting the model call behind a thin internal interface from day one is the cheapest insurance: it lets you test the two APIs against each other on your own traffic and switch whenever price or performance shifts, which for fast-moving reasoning models it inevitably will.&lt;/p&gt;

&lt;h2&gt;
  
  
  Key Takeaways
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;Reasoning models use internal thinking tokens to solve logical problems, outperforming standard chat models.&lt;/li&gt;
&lt;li&gt;OpenAI o3-mini is optimised for low-latency, real-time web applications requiring structured JSON formats.&lt;/li&gt;
&lt;li&gt;DeepSeek R1 is highly cost-effective and portable, allowing self-hosting to prevent vendor lock-in.&lt;/li&gt;
&lt;li&gt;Choose o3-mini for interactive development assistants; choose R1 for high-volume offline data analysis.&lt;/li&gt;
&lt;li&gt;Manage reasoning token sizes carefully to prevent unexpected API costs in production.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Integrate Reasoning Models into Your Stack
&lt;/h2&gt;

&lt;p&gt;Integrating advanced reasoning APIs requires careful prompt engineering, error handling, and hosting configurations. Mecanik provides professional &lt;a href="https://mecanik.dev/en/ai-integration-services/" rel="noopener noreferrer"&gt;AI integration services&lt;/a&gt; and custom setups through our &lt;a href="https://mecanik.dev/en/openai-api-integration/" rel="noopener noreferrer"&gt;OpenAI API integration service&lt;/a&gt;. We construct fast, secure AI pipelines tailored to your business. Contact us today to discuss your next project.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Related reading:&lt;/strong&gt; &lt;a href="https://mecanik.dev/en/posts/claude-opus-4-8-vs-gpt-5-api/" rel="noopener noreferrer"&gt;Claude Opus 4.8 vs. OpenAI GPT-5: Which API is Best?&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/ai-integration-cost-enterprise-budgeting-guide/" rel="noopener noreferrer"&gt;AI Integration Cost: 2026 Enterprise Budgeting Guide&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/claude-fable-5-hybrid-reasoning-api/" rel="noopener noreferrer"&gt;Claude Fable 5 Hybrid Reasoning: Thinking vs. Speed Modes&lt;/a&gt; and &lt;a href="https://mecanik.dev/en/posts/reduce-llm-latency-prompt-caching/" rel="noopener noreferrer"&gt;How to Reduce LLM Latency: Caching and Edge Strategies&lt;/a&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  Frequently Asked Questions (FAQ)
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;What is the difference between a reasoning model and a standard model?&lt;/strong&gt;&lt;br&gt;
Reasoning models use internal thinking tokens to analyse problems and debug logical steps before outputting a response, whereas standard models predict the next token immediately.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Can I host DeepSeek R1 on my own servers?&lt;/strong&gt;&lt;br&gt;
Yes. &lt;a href="https://www.deepseek.com/" rel="noopener noreferrer"&gt;DeepSeek R1&lt;/a&gt; is an open-source model with public weights, allowing you to self-host it on your own GPU infrastructure or deploy it on serverless runtimes.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Does OpenAI o3-mini support strict JSON schemas?&lt;/strong&gt;&lt;br&gt;
Yes. &lt;a href="https://openai.com/" rel="noopener noreferrer"&gt;OpenAI&lt;/a&gt;'s API supports structured outputs, guaranteeing that the model's output conforms exactly to the JSON schema you define in the API call.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;How does thinking token usage impact API costs?&lt;/strong&gt;&lt;br&gt;
Thinking tokens are billed as input and output tokens. Because the model must write out its internal reasoning steps, a single query uses more tokens than a standard API query.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Which model is better for code generation?&lt;/strong&gt;&lt;br&gt;
Both are excellent. OpenAI o3-mini is faster and more interactive, while DeepSeek R1 often provides deeper logic analysis on complex, multi-file software tasks.&lt;/p&gt;

</description>
      <category>serverless</category>
      <category>openai</category>
      <category>deepseek</category>
      <category>api</category>
    </item>
    <item>
      <title>Deploying Llama 3 on the Edge with Cloudflare Workers AI</title>
      <dc:creator>Mecanik1337</dc:creator>
      <pubDate>Mon, 05 Oct 2026 06:00:00 +0000</pubDate>
      <link>https://dev.to/mecanik-dev/deploying-llama-3-on-the-edge-with-cloudflare-workers-ai-2nf9</link>
      <guid>https://dev.to/mecanik-dev/deploying-llama-3-on-the-edge-with-cloudflare-workers-ai-2nf9</guid>
      <description>&lt;p&gt;This Cloudflare Workers AI tutorial shows you how to deploy and run machine learning models directly on Cloudflare's global edge network. With &lt;a href="https://developers.cloudflare.com/workers-ai/" rel="noopener noreferrer"&gt;Cloudflare Workers AI&lt;/a&gt;, you can execute Large Language Models (LLMs), text translation, image generation, and audio transcription close to your users without managing complex GPU servers. The steps below cover how to configure Wrangler, write a fetch handler, run a Llama model, and optimise API costs at the edge.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;TL;DR&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Run AI models serverless&lt;/strong&gt;; Cloudflare Workers AI manages the underlying GPU infrastructure, billing you only for active compute.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Configure bindings in wrangler.toml&lt;/strong&gt;; link your worker directly to the AI binding without managing API keys.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Write a fetch handler&lt;/strong&gt; to receive user requests, execute the model, and stream JSON responses.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Select optimised models&lt;/strong&gt; from Cloudflare's catalogue (such as Llama 3, Whisper, or Stable Diffusion) to balance speed and accuracy.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Silo billing and rate limits&lt;/strong&gt; to protect your endpoint from high-token cost abuse in production.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Why Run AI Models on the Edge?
&lt;/h2&gt;

&lt;p&gt;Traditionally, integrating AI features required calling external APIs (like OpenAI) or hosting open-source models on expensive cloud servers. &lt;/p&gt;

&lt;p&gt;Calling external APIs presents latency and data privacy concerns. Running your own GPU servers introduces maintenance challenges and scales poorly. Cloudflare Workers AI resolves this dilemma. The platform hosts open-source models on GPUs deployed across Cloudflare's global network. Your code runs as a lightweight Worker, executing models close to your users with near-zero latency. For an introduction to building basic edge structures, check our guide on &lt;a href="https://mecanik.dev/en/posts/building-a-serverless-api-with-cloudflare-workers/" rel="noopener noreferrer"&gt;building a serverless API with Cloudflare Workers&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Prerequisites
&lt;/h2&gt;

&lt;p&gt;Before you begin, make sure you have the following in place:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;A Cloudflare account&lt;/strong&gt; with Workers enabled. The free plan includes a daily inference allocation, which is more than enough to follow this guide.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Node.js 18 or newer&lt;/strong&gt; installed locally, so you can run the tooling and the local development server.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Wrangler, the Workers CLI, installed and authenticated.&lt;/strong&gt; Install it with &lt;code&gt;npm install -g wrangler&lt;/code&gt;, then run &lt;code&gt;wrangler login&lt;/code&gt; to link it to your account.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Basic familiarity with JavaScript&lt;/strong&gt; and the &lt;code&gt;fetch&lt;/code&gt; request/response model that every Worker is built around.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;If you are starting from a blank slate, scaffold a project with the create-cloudflare (C3) tool. It generates a ready-to-deploy Worker, a &lt;code&gt;wrangler.toml&lt;/code&gt;, and a sensible &lt;code&gt;compatibility_date&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm create cloudflare@latest my-edge-ai
&lt;span class="nb"&gt;cd &lt;/span&gt;my-edge-ai
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Choose the "Hello World" Worker template when prompted. That gives you a clean starting point to which you can add the AI binding in the next step.&lt;/p&gt;

&lt;h2&gt;
  
  
  Step 1: Configuring wrangler.toml
&lt;/h2&gt;

&lt;p&gt;To access AI models, you first need to define the AI binding in your project's configuration file.&lt;/p&gt;

&lt;p&gt;Open your &lt;code&gt;wrangler.toml&lt;/code&gt; (or &lt;code&gt;wrangler.json&lt;/code&gt;) and add the following block:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight toml"&gt;&lt;code&gt;&lt;span class="nn"&gt;[ai]&lt;/span&gt;
&lt;span class="py"&gt;binding&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;"AI"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This binding makes the AI service available on the environment argument (&lt;code&gt;env.AI&lt;/code&gt;) in your worker code. You do not need to manage API keys, configure endpoints, or deal with connection strings. Wrangler handles the authentication automatically when you deploy.&lt;/p&gt;

&lt;p&gt;A complete &lt;code&gt;wrangler.toml&lt;/code&gt; for this project looks like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight toml"&gt;&lt;code&gt;&lt;span class="py"&gt;name&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;"my-edge-ai"&lt;/span&gt;
&lt;span class="py"&gt;main&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;"src/index.js"&lt;/span&gt;
&lt;span class="py"&gt;compatibility_date&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;"2025-01-01"&lt;/span&gt;

&lt;span class="nn"&gt;[ai]&lt;/span&gt;
&lt;span class="py"&gt;binding&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;"AI"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;compatibility_date&lt;/code&gt; matters: it pins runtime behaviour so future platform changes cannot silently alter how your Worker runs. Omit it and deployment fails with a configuration error, which is one of the most common first-run stumbles.&lt;/p&gt;

&lt;h2&gt;
  
  
  Step 2: Writing the Worker Code
&lt;/h2&gt;

&lt;p&gt;Once the binding is configured, you can call the AI service from your &lt;code&gt;fetch&lt;/code&gt; handler. The example below shows how to receive a JSON payload containing a user prompt and generate a text completion using Llama 3.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;async&lt;/span&gt; &lt;span class="nf"&gt;fetch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;request&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;request&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;method&lt;/span&gt; &lt;span class="o"&gt;!==&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;POST&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;Response&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Method not allowed&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;status&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;405&lt;/span&gt; &lt;span class="p"&gt;});&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

    &lt;span class="k"&gt;try&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;prompt&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;request&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;json&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
      &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nx"&gt;prompt&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;Response&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;json&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="na"&gt;error&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Missing prompt&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;status&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;400&lt;/span&gt; &lt;span class="p"&gt;});&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;

      &lt;span class="c1"&gt;// Call the model using the AI binding&lt;/span&gt;
      &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;response&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;AI&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;run&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;@cf/meta/llama-3-8b-instruct&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="na"&gt;prompt&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;prompt&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="na"&gt;max_tokens&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;256&lt;/span&gt;
      &lt;span class="p"&gt;});&lt;/span&gt;

      &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;Response&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;json&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;response&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;catch &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;Response&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;json&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="na"&gt;error&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;err&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;message&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;status&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;500&lt;/span&gt; &lt;span class="p"&gt;});&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This simple structure allows you to build text summarisers, sentiment analysis tools, or content generators. If you want to connect these features to your database, you can bind to a serverless SQL database; see &lt;a href="https://mecanik.dev/en/posts/cloudflare-d1-build-a-serverless-sql-database-on-the-edge/" rel="noopener noreferrer"&gt;Cloudflare D1 database setup&lt;/a&gt; for details.&lt;/p&gt;

&lt;h3&gt;
  
  
  Using the chat message format
&lt;/h3&gt;

&lt;p&gt;The &lt;code&gt;prompt&lt;/code&gt; field is convenient for one-shot completions, but conversational models behave best with a structured &lt;code&gt;messages&lt;/code&gt; array. This lets you set a system instruction that shapes the model's tone and keep it separate from the user's input:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;messages&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
  &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;role&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;system&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;content&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;You are a concise technical assistant.&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;role&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;user&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;content&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;prompt&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;];&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;response&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;AI&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;run&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;@cf/meta/llama-3-8b-instruct&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nx"&gt;messages&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;max_tokens&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;512&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;

&lt;span class="c1"&gt;// Text models return the generated text on the `response` property&lt;/span&gt;
&lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;Response&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;json&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="na"&gt;answer&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;response&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;response&lt;/span&gt; &lt;span class="p"&gt;});&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Note that text-generation models wrap their output in a &lt;code&gt;response&lt;/code&gt; field, so the completed text lives at &lt;code&gt;response.response&lt;/code&gt; rather than at the top level. This catches out many first-time users, who log the raw object and see an unexpected shape.&lt;/p&gt;

&lt;h2&gt;
  
  
  Choosing the Right Model
&lt;/h2&gt;

&lt;p&gt;Cloudflare's catalogue includes dozens of models, and choosing well is a trade-off between speed, quality, and cost. Smaller models reply faster and consume fewer resources; larger models reason better but cost more per request. The table below compares a few popular text-generation options.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Model&lt;/th&gt;
&lt;th&gt;Best for&lt;/th&gt;
&lt;th&gt;Relative speed&lt;/th&gt;
&lt;th&gt;Relative cost&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;@cf/meta/llama-3-8b-instruct&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;General chat, summarisation&lt;/td&gt;
&lt;td&gt;Fast&lt;/td&gt;
&lt;td&gt;Low&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;@cf/meta/llama-3.1-70b-instruct&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;Complex reasoning, longer answers&lt;/td&gt;
&lt;td&gt;Slower&lt;/td&gt;
&lt;td&gt;Higher&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;@cf/mistral/mistral-7b-instruct-v0.2&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;Lightweight instructions, drafts&lt;/td&gt;
&lt;td&gt;Fast&lt;/td&gt;
&lt;td&gt;Low&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;@cf/meta/llama-guard-3-8b&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;Moderating and classifying content&lt;/td&gt;
&lt;td&gt;Fast&lt;/td&gt;
&lt;td&gt;Low&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;As a rule of thumb, start with an 8B model such as Llama 3 8B Instruct. It handles the majority of summarisation, classification, and chat workloads at a fraction of the latency and cost of a 70B model. Only move up to a larger model once your own evaluations show the smaller one genuinely falling short.&lt;/p&gt;

&lt;h2&gt;
  
  
  Step 3: Streaming Responses for Better User Experience
&lt;/h2&gt;

&lt;p&gt;For chat applications, waiting for the full response to generate can result in poor user experience. &lt;/p&gt;

&lt;p&gt;You can configure the AI binding to stream the response token by token as it generates. To achieve this, pass &lt;code&gt;stream: true&lt;/code&gt; in your request options. The worker will return a &lt;code&gt;ReadableStream&lt;/code&gt; that you can forward directly to the browser client, creating a fast, interactive chat interface. To compare this edge runtime approach with traditional cloud hosting, read our comparison of &lt;a href="https://mecanik.dev/en/posts/cloudflare-workers-vs-aws-lambda-2026/" rel="noopener noreferrer"&gt;Cloudflare Workers vs AWS Lambda&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Here is a complete streaming handler. Rather than returning parsed JSON, you forward the stream to the client with the correct &lt;code&gt;content-type&lt;/code&gt; so the browser can consume it as Server-Sent Events:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;async&lt;/span&gt; &lt;span class="nf"&gt;fetch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;request&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;prompt&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;request&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;json&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;stream&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;AI&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;run&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;@cf/meta/llama-3-8b-instruct&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="nx"&gt;prompt&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;max_tokens&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;512&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;stream&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
    &lt;span class="p"&gt;});&lt;/span&gt;

    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;Response&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;stream&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="na"&gt;headers&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;content-type&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;text/event-stream&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;});&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The key difference from the non-streaming version is the response itself: you pass the stream straight into &lt;code&gt;new Response()&lt;/code&gt; and set &lt;code&gt;content-type&lt;/code&gt; to &lt;code&gt;text/event-stream&lt;/code&gt;. Wrap a stream in &lt;code&gt;Response.json()&lt;/code&gt; instead and it will not serialise correctly, so the client receives an empty body.&lt;/p&gt;

&lt;h2&gt;
  
  
  Testing and Deploying Your Worker
&lt;/h2&gt;

&lt;p&gt;With the binding and handler in place, run the Worker locally before you ship it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npx wrangler dev
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Because inference runs on Cloudflare's GPUs rather than on your machine, the AI binding reaches out to the network even during local development. Wrangler manages this for you, but it does mean local testing needs connectivity and a valid login to work.&lt;/p&gt;

&lt;p&gt;Send a test request with &lt;code&gt;curl&lt;/code&gt; while &lt;code&gt;wrangler dev&lt;/code&gt; is running:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://localhost:8787 &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"prompt": "Summarise the benefits of edge computing in one sentence."}'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Once you are happy with the output, deploy to the global network:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npx wrangler deploy
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Wrangler uploads your Worker and returns a &lt;code&gt;*.workers.dev&lt;/code&gt; URL. Your endpoint is now live in every Cloudflare data centre, and each request is routed to the location closest to the user automatically.&lt;/p&gt;

&lt;h2&gt;
  
  
  Common Pitfalls and Troubleshooting
&lt;/h2&gt;

&lt;p&gt;A handful of issues recur when teams first deploy inference at the edge. Knowing the fix in advance saves hours of debugging.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;&lt;code&gt;Cannot read properties of undefined (reading 'run')&lt;/code&gt;&lt;/strong&gt; — the &lt;code&gt;env.AI&lt;/code&gt; binding is undefined. This almost always means the &lt;code&gt;[ai]&lt;/code&gt; block is missing from &lt;code&gt;wrangler.toml&lt;/code&gt;, or you edited the file but did not restart &lt;code&gt;wrangler dev&lt;/code&gt; (or redeploy). Confirm the binding name matches exactly.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;code&gt;No such model&lt;/code&gt; or a 400 error on &lt;code&gt;run&lt;/code&gt;&lt;/strong&gt; — the model identifier is wrong. Model names are case-sensitive and must include the full path, for example &lt;code&gt;@cf/meta/llama-3-8b-instruct&lt;/code&gt;. Copy them from the model catalogue rather than typing from memory.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Empty or malformed streamed responses&lt;/strong&gt; — you returned the stream through &lt;code&gt;Response.json()&lt;/code&gt; instead of &lt;code&gt;new Response(stream, ...)&lt;/code&gt;. Streams must be forwarded, not serialised.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Capacity or 429 errors under load&lt;/strong&gt; — the model is temporarily saturated or you have hit an account limit. Add a short retry with back-off, and consider a smaller model for bursts of traffic.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Truncated answers&lt;/strong&gt; — the reply stops mid-sentence because &lt;code&gt;max_tokens&lt;/code&gt; is too low. Raise the limit, but remember that larger values increase both latency and cost.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;If a request fails silently, watch the live logs with &lt;code&gt;npx wrangler tail&lt;/code&gt; while you send a test request. It streams runtime errors and &lt;code&gt;console.log&lt;/code&gt; output from the deployed Worker, which is the quickest way to see what the model actually returned.&lt;/p&gt;

&lt;h2&gt;
  
  
  Optimising Production Costs and Security
&lt;/h2&gt;

&lt;p&gt;While Workers AI is highly cost-effective, running model inference in production requires careful controls.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Implement Rate Limiting&lt;/strong&gt;: Limit how often a client can call your endpoint. GPU compute costs scale with usage.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Sanitise Prompts&lt;/strong&gt;: Validate inputs to prevent injection attacks and ensure the model outputs stay on brand.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Silo Context Size&lt;/strong&gt;: Keep prompt histories short. Sending massive context buffers on each call increases token processing costs.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;For a detailed look at context management, check our guide on &lt;a href="https://mecanik.dev/en/posts/building-an-ai-chatbot-with-the-openai-api/" rel="noopener noreferrer"&gt;building an OpenAI API chatbot&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Key Takeaways
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;Cloudflare Workers AI provides serverless access to open-source models without GPU maintenance.&lt;/li&gt;
&lt;li&gt;Configure access by adding the &lt;code&gt;[ai]&lt;/code&gt; binding block to your &lt;code&gt;wrangler.toml&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;Write fetch handlers to execute text generation, translation, or image tasks directly at the edge.&lt;/li&gt;
&lt;li&gt;Enable token streaming with &lt;code&gt;stream: true&lt;/code&gt; to optimise mobile and chat experiences.&lt;/li&gt;
&lt;li&gt;Implement rate limits and prompt sanitisation to protect your edge endpoints in production.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Build Your AI Applications on the Edge
&lt;/h2&gt;

&lt;p&gt;Building reliable AI integrations requires expert knowledge of serverless architecture. Mecanik specialises in &lt;a href="https://mecanik.dev/en/ai-integration-services/" rel="noopener noreferrer"&gt;AI integration services&lt;/a&gt; and custom API setups through our &lt;a href="https://mecanik.dev/en/openai-api-integration/" rel="noopener noreferrer"&gt;OpenAI API integration service&lt;/a&gt;. We build edge-native tools that scale seamlessly, optimising costs and user experiences. Contact us today to discuss your project requirements.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Related reading:&lt;/strong&gt; &lt;a href="https://mecanik.dev/en/posts/reduce-llm-latency-prompt-caching/" rel="noopener noreferrer"&gt;How to Reduce LLM Latency: Caching and Edge Strategies&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/cloudflare-workers-ai-agent/" rel="noopener noreferrer"&gt;Building AI Agents with Cloudflare Workers and LangChain&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/claude-fable-5-hybrid-reasoning-api/" rel="noopener noreferrer"&gt;Claude Fable 5 Hybrid Reasoning: Thinking vs. Speed Modes&lt;/a&gt; and &lt;a href="https://mecanik.dev/en/posts/openai-realtime-api-voice-agent/" rel="noopener noreferrer"&gt;Build Voice Agents: OpenAI Realtime API Guide&lt;/a&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  Frequently Asked Questions (FAQ)
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;What is Cloudflare Workers AI?&lt;/strong&gt;&lt;br&gt;
It is a serverless platform that allows you to run machine learning models (text generation, translation, speech-to-text, image generation) on Cloudflare's global GPU network.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Do I need an API key to use Workers AI?&lt;/strong&gt;&lt;br&gt;
No. Once you declare the AI binding in your &lt;code&gt;wrangler.toml&lt;/code&gt; file, Cloudflare handles credentials internally, making the service accessible via &lt;code&gt;env.AI&lt;/code&gt; as shown in this cloudflare workers ai tutorial.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;What models are available on Cloudflare Workers AI?&lt;/strong&gt;&lt;br&gt;
The platform hosts popular open-source models, including Meta Llama, Mistral, OpenAI Whisper, and Stable Diffusion, which are updated regularly in their model catalogue.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Can I stream text responses from Workers AI?&lt;/strong&gt;&lt;br&gt;
Yes. By setting &lt;code&gt;stream: true&lt;/code&gt; in the parameters of your &lt;code&gt;env.AI.run&lt;/code&gt; call, the worker returns a standard &lt;code&gt;ReadableStream&lt;/code&gt; to stream text to the browser.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;How does billing work for Workers AI?&lt;/strong&gt;&lt;br&gt;
Billing is based on the number of tokens processed (for text models) or the duration of compute time (for other models), offering a cost-effective utility model.&lt;/p&gt;

</description>
      <category>serverless</category>
      <category>ai</category>
    </item>
    <item>
      <title>Drupal Migration in 2026: Costs, Options and Deadlines</title>
      <dc:creator>Mecanik1337</dc:creator>
      <pubDate>Sun, 04 Oct 2026 18:00:00 +0000</pubDate>
      <link>https://dev.to/mecanik-dev/drupal-migration-in-2026-costs-options-and-deadlines-1h7o</link>
      <guid>https://dev.to/mecanik-dev/drupal-migration-in-2026-costs-options-and-deadlines-1h7o</guid>
      <description>&lt;p&gt;Drupal migration is one of those projects that stays comfortably in next quarter's plan until a date makes it urgent. Two dates are doing that right now, and only one of them is in the future.&lt;/p&gt;

&lt;p&gt;Drupal 7 lost official support on 5 January 2025. Any site still running it has been going without security coverage for well over a year. Drupal 10 reaches end of life on 9 December 2026, the same week Drupal 12 is released, after which it receives no further releases of any kind. If you are on either version, the question is no longer whether to move but which path to take and what it will cost.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Where you stand:&lt;/strong&gt; From Drupal 10 to Drupal 11 is a genuine upgrade — the same site, updated in place, typically two to six weeks. From Drupal 7 to Drupal 11 is not an upgrade at all; it is a rebuild with a content migration attached, and it typically runs three to six months. Confusing the two is the single most expensive mistake in this space, because Drupal 7 sites get quoted as upgrades and then overrun by a factor of four.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  The Two Very Different Migrations
&lt;/h2&gt;

&lt;p&gt;The word migration covers two jobs that share almost nothing beyond the name.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Drupal 10 to 11 is an upgrade.&lt;/strong&gt; The architecture is the same. Your entities, fields, views and configuration carry across. The work is mostly dependency management: making sure every contributed module has a Drupal 11 compatible release, clearing deprecated API calls out of your custom code, and moving to a supported PHP version. It is methodical rather than difficult, and a well-maintained site can be done in a fortnight.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Drupal 7 to Drupal 11 is a rebuild.&lt;/strong&gt; Drupal 8 rewrote the platform on Symfony components, replacing the module API, the theming layer and the configuration system. Nothing carries over automatically except content, and even that arrives through a purpose-built migration process rather than an upgrade script. Your modules do not exist any more, your theme has to be rewritten in Twig, and your custom code has to be reimplemented against a different architecture.&lt;/p&gt;

&lt;p&gt;That second case is why Drupal 7 sites have lingered so long. The honest framing is that you are not upgrading a site, you are building a new one and bringing the content with you.&lt;/p&gt;




&lt;h2&gt;
  
  
  What Each Drupal Migration Path Costs
&lt;/h2&gt;

&lt;p&gt;Figures below assume UK agency rates and a site of moderate complexity. Complexity here means the number of content types, contributed modules and custom modules, not the number of pages.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Drupal 10 to 11, well-maintained site.&lt;/strong&gt; Two to four weeks, roughly £6,000 to £15,000. This is the happy case: modules are current, custom code is small, and the main work is testing.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Drupal 10 to 11, neglected site.&lt;/strong&gt; Four to eight weeks, roughly £15,000 to £35,000. Here the blockers are contributed modules with no Drupal 11 release, custom code written against APIs that have since been removed, and a PHP version that also has to move. Every abandoned module becomes a decision: find a replacement, take over maintenance, or reimplement its behaviour.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Drupal 7 to Drupal 11.&lt;/strong&gt; Three to six months, commonly £40,000 to £120,000 and higher for large or heavily customised sites. That range is wide because it is really a rebuild budget. The content migration itself is often the smaller half; the theme, the custom functionality and the integrations are the larger half.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Drupal 7 to a different platform.&lt;/strong&gt; Sometimes the right answer. If the original reason for choosing Drupal no longer applies — the site has become a straightforward marketing site with a blog — then moving to something simpler can cost less than migrating within Drupal, and reduce running costs afterwards. Our comparison of &lt;a href="https://mecanik.dev/en/posts/wordpress-vs-custom-web-development-what-uk-businesses-need-to-know/" rel="noopener noreferrer"&gt;WordPress and custom web development&lt;/a&gt; covers where that line sits, and the &lt;a href="https://mecanik.dev/en/posts/drupal-web-development-a-2026-guide/" rel="noopener noreferrer"&gt;Drupal web development guide&lt;/a&gt; is honest about when Drupal is not the answer.&lt;/p&gt;




&lt;h2&gt;
  
  
  Why Contributed Modules Decide Your Timeline
&lt;/h2&gt;

&lt;p&gt;Almost every Drupal upgrade estimate lives or dies on the contrib audit, and it is the first thing worth doing.&lt;/p&gt;

&lt;p&gt;List every contributed module the site uses, then check each one for a stable release compatible with your target version. What you will find falls into four groups. Some have a compatible release and need nothing. Some have a release candidate or a patch in the issue queue that you can apply through Composer. Some have been abandoned, and you must find a replacement, adopt the module yourself, or replace its function with custom code. And some have been absorbed into Drupal core, which is the pleasant surprise of the exercise.&lt;/p&gt;

&lt;p&gt;That audit converts a vague project into a countable one. Until it is done, any quote is a guess, and a supplier who gives you a fixed price without it is either padding heavily or about to raise change requests.&lt;/p&gt;

&lt;p&gt;The same logic applies to custom modules, with a different tool. Drupal's deprecation tooling will scan custom code and report calls to APIs that have been removed or are due for removal, which turns "we have some custom code" into a specific list of files and line numbers.&lt;/p&gt;




&lt;h2&gt;
  
  
  What Actually Goes Wrong
&lt;/h2&gt;

&lt;p&gt;Certain failure modes recur across almost every Drupal migration.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Configuration drift between environments.&lt;/strong&gt; If changes have been made directly in the production admin interface rather than exported to configuration files, your staging environment is not a faithful copy and your testing is worth less than you think. Discovering this mid-migration is common and it always costs time.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Content that was never as structured as everyone believed.&lt;/strong&gt; Drupal 7 sites frequently accumulated content in ways nobody documented: fields repurposed for other things, a taxonomy vocabulary doing the job of a workflow state, HTML pasted into body fields carrying inline styles. A migration surfaces all of it at once, and each case needs a decision from someone who knows what the content is for.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Media and file handling.&lt;/strong&gt; Drupal's media handling changed substantially after Drupal 7. Files, image styles and embedded media rarely map one to one, and sites with large media libraries should budget for this specifically rather than assuming it comes free with the content migration.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;URL and SEO continuity.&lt;/strong&gt; This is the one that damages the business rather than the schedule. If URL aliases change without redirects, you lose the rankings the old site earned. Every migration needs a full URL inventory, a redirect map, and verification after launch. Our guide to &lt;a href="https://mecanik.dev/en/posts/website-migration-without-losing-traffic/" rel="noopener noreferrer"&gt;migrating a website without losing traffic&lt;/a&gt; covers that process in detail, and it applies to platform changes just as much as domain changes.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Multilingual content.&lt;/strong&gt; If the site runs in several languages, expect the migration to take substantially longer. Language handling was rebuilt after Drupal 7, and translated content, translated configuration and language-specific URL patterns each need their own attention.&lt;/p&gt;




&lt;h2&gt;
  
  
  How to Sequence the Work
&lt;/h2&gt;

&lt;p&gt;The order matters more than most teams expect, and getting it wrong causes rework.&lt;/p&gt;

&lt;p&gt;Start with the contrib and custom code audit, before any estimating. Then get the site onto a supported PHP version and the latest release of its current major version, because that removes a whole category of noise from the actual upgrade. Only then attempt the major version step.&lt;/p&gt;

&lt;p&gt;Build the new environment alongside the old one rather than upgrading in place. That gives you somewhere to test the content migration repeatedly, which you will need, because migrations are run many times before they are run once for real.&lt;/p&gt;

&lt;p&gt;Treat the content migration as code. Drupal's migration framework lets you define migrations in configuration and re-run them, which means you can reset, adjust the mapping and go again. Teams that hand-fix content in the new site rather than fixing the migration definition end up unable to re-run it, and then a single content change in the old site becomes a manual reconciliation.&lt;/p&gt;

&lt;p&gt;Finally, plan a content freeze near the end, and keep it short. Long freezes cause editors to work around you, which produces exactly the drift you were trying to avoid.&lt;/p&gt;




&lt;h2&gt;
  
  
  Should You Move Off Drupal Entirely?
&lt;/h2&gt;

&lt;p&gt;It is a fair question and it deserves an honest answer rather than a defensive one.&lt;/p&gt;

&lt;p&gt;Stay on Drupal when the reasons you chose it still hold: complex content modelling, granular permissions, multilingual requirements, heavy editorial workflow, or accessibility and public sector obligations. Drupal remains genuinely strong at all of these and the upgrade path from here is now stable, with a predictable two-year major release cycle.&lt;/p&gt;

&lt;p&gt;Consider moving when the site has drifted away from those needs. Plenty of Drupal 7 sites are now, in practice, a marketing site with news and a contact form. Migrating that within Drupal means paying rebuild prices for capability you no longer use.&lt;/p&gt;

&lt;p&gt;The decision should turn on the content model and the editorial workload, not on which platform your developer prefers. If nobody can articulate what Drupal is doing for you that a simpler platform could not, that is informative.&lt;/p&gt;




&lt;h2&gt;
  
  
  Get the Audit Before You Get a Quote
&lt;/h2&gt;

&lt;p&gt;Mecanik handles Drupal upgrades and migrations as part of our &lt;a href="https://mecanik.dev/en/services/website-development/" rel="noopener noreferrer"&gt;website development services&lt;/a&gt;. We start with the contrib and custom code audit, because that is what turns an open-ended project into a fixed scope, and it is worth having even if you then take the work elsewhere.&lt;/p&gt;

&lt;p&gt;For Drupal 10 sites the sensible move is to plan the Drupal 11 step now rather than in November, when everyone else is doing it. For Drupal 7 sites the security position is already the argument. If your constraint is capacity rather than expertise, our guide to &lt;a href="https://mecanik.dev/en/posts/hire-drupal-developer-rates-skills-vetting/" rel="noopener noreferrer"&gt;hiring a Drupal developer&lt;/a&gt; covers what to look for.&lt;/p&gt;

&lt;p&gt;Tell us which version you are on and roughly how many contributed and custom modules the site uses, and we will tell you which of the paths above you are actually facing.&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;Related reading:&lt;/strong&gt; &lt;a href="https://mecanik.dev/en/posts/legacy-php-modernisation-guide/" rel="noopener noreferrer"&gt;Legacy PHP Modernisation: A 2026 Guide&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/symfony-vs-laravel-2026/" rel="noopener noreferrer"&gt;Symfony vs Laravel in 2026: Which PHP Framework to Choose&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/api-security-protect-public-api/" rel="noopener noreferrer"&gt;API Security: How to Protect a Public API in 2026&lt;/a&gt; and &lt;a href="https://mecanik.dev/en/posts/medical-and-healthcare-website-development-in-the-uk/" rel="noopener noreferrer"&gt;Medical &amp;amp; Healthcare Website Development UK 2026&lt;/a&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  Frequently Asked Questions
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;When does Drupal 10 stop being supported?&lt;/strong&gt;&lt;br&gt;
Drupal 10 reaches end of life on 9 December 2026, the same week Drupal 12 is released. After that date it receives no further releases, including security fixes, so any site remaining on it is running unsupported.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;How much does a Drupal migration cost?&lt;/strong&gt;&lt;br&gt;
A Drupal 10 to 11 upgrade on a well-maintained site typically costs £6,000 to £15,000, rising to £15,000 to £35,000 where modules and custom code are neglected. Drupal 7 to Drupal 11 is a rebuild with content migration and commonly runs £40,000 to £120,000 or more.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Why is Drupal 7 to Drupal 11 so much more expensive?&lt;/strong&gt;&lt;br&gt;
Because it is not an upgrade. Drupal 8 rebuilt the platform on Symfony components, replacing the module API, theming layer and configuration system. Modules must be replaced, themes rewritten in Twig and custom code reimplemented, with content brought across through a purpose-built migration.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;How long does a Drupal 10 to 11 upgrade take?&lt;/strong&gt;&lt;br&gt;
Two to four weeks for a site whose contributed modules are current and custom code is small, and four to eight weeks where abandoned modules or removed APIs have to be worked around. A contributed module audit up front is what makes the estimate reliable.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Can I migrate from Drupal to WordPress instead?&lt;/strong&gt;&lt;br&gt;
Sometimes that is the right call, particularly where a Drupal 7 site has become a straightforward marketing site with no complex content modelling, permissions or multilingual needs. Base the decision on your content model and editorial workload rather than on platform preference.&lt;/p&gt;

</description>
      <category>php</category>
      <category>refactoring</category>
      <category>webdev</category>
      <category>architecture</category>
    </item>
    <item>
      <title>COBOL Migration Cost, Timeline and Risk - A UK Guide 2026</title>
      <dc:creator>Mecanik1337</dc:creator>
      <pubDate>Sun, 04 Oct 2026 06:00:00 +0000</pubDate>
      <link>https://dev.to/mecanik-dev/cobol-migration-cost-timeline-and-risk-a-uk-guide-2026-5eon</link>
      <guid>https://dev.to/mecanik-dev/cobol-migration-cost-timeline-and-risk-a-uk-guide-2026-5eon</guid>
      <description>&lt;p&gt;"How much will it cost to move off COBOL?" is the first question every board asks, and the honest answer is that it depends on more than the size of the codebase. This guide breaks down what actually drives the cost of a COBOL migration in the UK, realistic budget and timeline ranges, and the risks that turn a well-planned project into an overrun.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;TL;DR&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;A mid-size UK COBOL migration typically costs £200,000 to £800,000 and takes one to two years; full mainframe decommissions run into the millions and multiple years&lt;/li&gt;
&lt;li&gt;Cost is driven far more by codebase complexity, undocumented business logic, and data access redesign than by raw line count&lt;/li&gt;
&lt;li&gt;The choice of target language and migration approach materially changes the budget&lt;/li&gt;
&lt;li&gt;The most common reason projects overrun is underestimating scope, especially undocumented business rules and the data access layer&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  What Actually Drives COBOL Migration Cost
&lt;/h2&gt;

&lt;p&gt;Line count is the headline number, but it is a weak predictor on its own. The real cost drivers are:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Complexity, not just size.&lt;/strong&gt; A 100,000-line system of clean batch programs is cheaper to migrate than a 50,000-line system dense with &lt;code&gt;EXEC CICS&lt;/code&gt;, dynamic &lt;code&gt;CALL&lt;/code&gt;s, and intricate &lt;code&gt;REDEFINES&lt;/code&gt;. Transaction processing systems cost more than batch systems of the same size.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Undocumented business logic.&lt;/strong&gt; COBOL systems often carry 30 to 40 years of business rules embedded in code with no external documentation. Rediscovering and validating those rules is frequently the single largest and least predictable line item.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The data access layer.&lt;/strong&gt; &lt;code&gt;EXEC SQL&lt;/code&gt; against DB2 and VSAM file handling rarely convert automatically. They must be redesigned onto the target platform's data access technology, and this is often the biggest work item after business-logic discovery.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Data format conversion.&lt;/strong&gt; Packed decimal (&lt;code&gt;COMP-3&lt;/code&gt;), EBCDIC encoding, and fixed-width layouts all need explicit mapping and testing with real data.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Target language and approach.&lt;/strong&gt; These shift the budget in predictable ways (covered below).&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Testing and cut-over.&lt;/strong&gt; Building a regression test suite that proves output parity, and executing a safe cut-over with rollback, is real, non-trivial effort that inexperienced estimates omit.&lt;/p&gt;

&lt;h2&gt;
  
  
  Indicative Cost and Timeline Ranges (UK)
&lt;/h2&gt;

&lt;p&gt;These ranges cover analysis, migration, testing, and go-live support. They exclude ongoing operational costs, training, and downstream integration work that often surfaces mid-project.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;System Size&lt;/th&gt;
&lt;th&gt;Approach&lt;/th&gt;
&lt;th&gt;Estimated Cost&lt;/th&gt;
&lt;th&gt;Typical Timeline&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Small (&amp;lt; 50,000 lines)&lt;/td&gt;
&lt;td&gt;Parallel rewrite&lt;/td&gt;
&lt;td&gt;£80,000 to £200,000&lt;/td&gt;
&lt;td&gt;3 to 9 months&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Medium (50,000 to 500,000 lines)&lt;/td&gt;
&lt;td&gt;Strangler fig&lt;/td&gt;
&lt;td&gt;£200,000 to £800,000&lt;/td&gt;
&lt;td&gt;12 to 24 months&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Large (500,000+ lines)&lt;/td&gt;
&lt;td&gt;Automated + incremental refactor&lt;/td&gt;
&lt;td&gt;£500,000 to £2,000,000+&lt;/td&gt;
&lt;td&gt;2 to 4 years&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Legacy mainframe decommission&lt;/td&gt;
&lt;td&gt;Full programme&lt;/td&gt;
&lt;td&gt;£1,000,000 to £10,000,000+&lt;/td&gt;
&lt;td&gt;3 to 5 years+&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Treat these as planning ranges, not quotes. A proper estimate requires a code assessment; the spread within each band is driven by the complexity factors above.&lt;/p&gt;

&lt;h2&gt;
  
  
  How the Target Language Affects Cost
&lt;/h2&gt;

&lt;p&gt;The destination language changes both the effort profile and the long-term cost of ownership. In broad terms:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://mecanik.dev/en/posts/cobol-to-python-migration-a-uk-enterprise-guide/" rel="noopener noreferrer"&gt;Python&lt;/a&gt;&lt;/strong&gt; maps naturally to COBOL's procedural style and has the largest developer pool, which tends to lower conversion and long-term maintenance cost.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://mecanik.dev/en/posts/cobol-to-csharp-migration-a-uk-enterprise-guide/" rel="noopener noreferrer"&gt;C#&lt;/a&gt;&lt;/strong&gt; is efficient for organisations already on the .NET and Azure stack, and its native &lt;code&gt;decimal&lt;/code&gt; type reduces the effort of getting financial precision right.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://mecanik.dev/en/posts/cobol-to-java-migration-a-uk-enterprise-guide/" rel="noopener noreferrer"&gt;Java&lt;/a&gt;&lt;/strong&gt; suits JVM-based enterprises; &lt;code&gt;BigDecimal&lt;/code&gt; handles precision correctly but adds some verbosity.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://mecanik.dev/en/posts/cobol-to-go-migration-a-uk-enterprise-guide/" rel="noopener noreferrer"&gt;Go&lt;/a&gt;&lt;/strong&gt; is efficient to build and deploy, but the lack of a native decimal type adds review effort for financial fields.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://mecanik.dev/en/posts/cobol-to-rust-migration-a-uk-enterprise-guide/" rel="noopener noreferrer"&gt;Rust&lt;/a&gt;&lt;/strong&gt; tends toward the upper end of any size band because its ownership model adds up-front design effort.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The &lt;a href="https://mecanik.dev/en/cobol-migration/" rel="noopener noreferrer"&gt;COBOL migration overview&lt;/a&gt; compares all six target languages side by side to help you choose.&lt;/p&gt;

&lt;h2&gt;
  
  
  How the Migration Approach Affects Cost
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Automated conversion&lt;/strong&gt; reduces the mechanical translation effort but never produces a finished system; budget for the manual work the tooling flags (embedded SQL, CICS, dynamic calls, decimal precision).&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Parallel rewrite&lt;/strong&gt; roughly doubles operational cost during the transition because two systems run at once, but it minimises continuity risk. It suits smaller, mission-critical systems.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Incremental (&lt;a href="https://martinfowler.com/bliki/StranglerFigApplication.html" rel="noopener noreferrer"&gt;strangler fig&lt;/a&gt;)&lt;/strong&gt; spreads cost over time and reduces big-bang risk, at the price of a longer hybrid period. It is the most common approach for large UK enterprise systems.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Most real projects blend automated conversion with an incremental rollout.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Risks That Cause Overruns
&lt;/h2&gt;

&lt;p&gt;Migrations overrun for predictable reasons. The big five:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Underestimated business-logic discovery.&lt;/strong&gt; The rules are in the code, not in a document. Budget explicit discovery time.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Data access redesign.&lt;/strong&gt; DB2 and VSAM access does not port automatically. Treat it as its own workstream.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Inadequate regression testing.&lt;/strong&gt; Without output-parity testing on real data, you cannot prove the migration is correct. Build the test suite before migration starts.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Decimal precision errors.&lt;/strong&gt; Financial fields mapped to floating-point types silently corrupt money. Map to the correct decimal type for the target language.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Cut-over failure.&lt;/strong&gt; The switch to production is the highest-risk moment. A detailed cut-over plan with rollback and reconciliation is mandatory.&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  How to Get an Accurate Estimate
&lt;/h2&gt;

&lt;p&gt;A reliable number comes from a code assessment, not a line count. A good assessment inventories programs and copybooks, identifies &lt;code&gt;EXEC SQL&lt;/code&gt; / &lt;code&gt;EXEC CICS&lt;/code&gt; / dynamic-call hotspots, gauges business-logic density, and maps the data access surface. The &lt;a href="https://mecanik.dev/en/services/cobol-migration/" rel="noopener noreferrer"&gt;Mecanik COBOL migration service&lt;/a&gt; provides UK enterprise assessments and full-service migration; for mainframe estates on IBM z/OS, the &lt;a href="https://mecanik.dev/en/legacy-mainframe-migration/" rel="noopener noreferrer"&gt;legacy mainframe migration service&lt;/a&gt; covers the infrastructure decommission alongside the code.&lt;/p&gt;

&lt;h2&gt;
  
  
  Key Takeaways
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;A mid-size UK COBOL migration typically costs £200,000 to £800,000 over one to two years; mainframe decommissions run into the millions.&lt;/li&gt;
&lt;li&gt;Complexity, undocumented business logic, and data access redesign drive cost far more than line count.&lt;/li&gt;
&lt;li&gt;Target language and migration approach both move the budget in predictable ways.&lt;/li&gt;
&lt;li&gt;Overruns come from underestimating discovery, testing, and cut-over; a proper code assessment is the only reliable basis for a quote.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Related reading:&lt;/strong&gt; &lt;a href="https://mecanik.dev/en/posts/cobol-modernisation-services-choosing-a-vendor/" rel="noopener noreferrer"&gt;COBOL Modernisation Services: How to Choose a Vendor&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/mainframe-migration-tools-what-works/" rel="noopener noreferrer"&gt;Mainframe Migration Tools: What Works and What Fails&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/mainframe-modernisation-rewrite-refactor-replatform/" rel="noopener noreferrer"&gt;Mainframe Modernisation: Rewrite, Refactor or Replatform&lt;/a&gt; and &lt;a href="https://mecanik.dev/en/posts/cobol-to-java-migration-a-uk-enterprise-guide/" rel="noopener noreferrer"&gt;COBOL to Java Migration - A UK Enterprise Guide 2026&lt;/a&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  Frequently Asked Questions (FAQ)
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;How much does a COBOL migration cost in the UK?&lt;/strong&gt;&lt;br&gt;
A small system typically costs £80,000 to £200,000, a mid-size system £200,000 to £800,000, and large systems £500,000 upward. Full mainframe decommission programmes run from £1,000,000 into the tens of millions. Complexity, not line count, sets where you land in the range.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;How long does a COBOL migration take?&lt;/strong&gt;&lt;br&gt;
Small, well-documented systems take three to nine months. Mid-size enterprise systems run twelve to twenty-four months. Large mainframe programmes take three to five years or more for full decommission.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Why do COBOL migration costs vary so much?&lt;/strong&gt;&lt;br&gt;
Because complexity varies enormously. Undocumented business logic, embedded SQL and CICS, data format conversion, the target language, and the migration approach all move the cost. Two systems of the same line count can differ by an order of magnitude.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Does automated conversion reduce the cost?&lt;/strong&gt;&lt;br&gt;
It reduces mechanical translation effort, but no tool produces a finished system. You still budget for the data access layer, decimal-precision decisions, testing, and cut-over that the tooling flags for manual work.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;What is the biggest cause of COBOL migration overruns?&lt;/strong&gt;&lt;br&gt;
Underestimating scope, especially undocumented business logic and the data access redesign. Building a regression test suite for output parity before migration begins is the single most effective way to control that risk.&lt;/p&gt;

</description>
      <category>programming</category>
      <category>refactoring</category>
      <category>architecture</category>
    </item>
    <item>
      <title>WordPress Hacked: Malware Removal and Recovery Guide</title>
      <dc:creator>Mecanik1337</dc:creator>
      <pubDate>Sat, 03 Oct 2026 18:00:00 +0000</pubDate>
      <link>https://dev.to/mecanik-dev/wordpress-hacked-malware-removal-and-recovery-guide-1je7</link>
      <guid>https://dev.to/mecanik-dev/wordpress-hacked-malware-removal-and-recovery-guide-1je7</guid>
      <description>&lt;p&gt;If your WordPress site was hacked and is now showing pharmaceutical spam, redirecting visitors to somewhere unpleasant, or has been flagged by Google as deceptive, start here rather than with a plugin. The instinct is to install a security scanner and click clean. That removes the visible symptom and leaves the way in, which is why so many sites get reinfected within days and their owners conclude that WordPress is simply insecure.&lt;/p&gt;

&lt;p&gt;It is not. Almost every compromise arrives through an out-of-date plugin, and almost every failed cleanup happens because someone removed the malware without removing the access.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;First hour:&lt;/strong&gt; Take the site offline or into maintenance mode. Change the hosting control panel password, the database password, all administrator passwords and the FTP or SSH credentials. Do not restore a backup yet, and do not delete anything yet. You need the current state to work out how they got in, and a restore destroys that evidence while very likely reinstating the same vulnerability.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  What to Do in the First Hour
&lt;/h2&gt;

&lt;p&gt;Order matters here, and the common mistakes are all impatience.&lt;/p&gt;

&lt;p&gt;Take the site down. A maintenance page or a temporary block at the hosting or CDN level protects visitors and stops the site distributing malware while you work. If the site is serving malicious redirects, every hour it stays up compounds the reputational damage.&lt;/p&gt;

&lt;p&gt;Rotate every credential, not just the WordPress admin password. That means hosting panel, database user, FTP and SSH keys, and any API keys stored in the site's configuration. Attackers routinely create a second administrator account or leave a key behind, so changing one password achieves nothing.&lt;/p&gt;

&lt;p&gt;Preserve the evidence before changing anything. Take a full copy of the files and database as they are now, and download the server access logs covering at least the last thirty days. Those logs are how you find the entry point, and many hosts rotate them within days.&lt;/p&gt;

&lt;p&gt;Then, and only then, work out what happened.&lt;/p&gt;




&lt;h2&gt;
  
  
  How Your WordPress Site Got Hacked: Finding the Entry Point
&lt;/h2&gt;

&lt;p&gt;Cleaning without diagnosis is why reinfection is so common. Four checks find the cause in most cases.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Check plugin and theme versions against known vulnerabilities.&lt;/strong&gt; Out-of-date plugins are far and away the leading cause. Note every plugin, its version, and whether a security release exists that you have not applied. Pay particular attention to anything with an expired licence, because premium plugins stop receiving updates when the licence lapses while continuing to appear installed and active.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Read the access logs around the first sign of trouble.&lt;/strong&gt; You are looking for POST requests to unusual paths, requests to files that should not exist, and a burst of activity from one address shortly before the defacement. This is usually where the answer is.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Look for files that do not belong.&lt;/strong&gt; Recently modified PHP files in the uploads directory are a strong signal, because nothing should ever execute there. So are files with names designed to look plausible, and modifications to &lt;code&gt;wp-config.php&lt;/code&gt; or &lt;code&gt;.htaccess&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Check for added administrator accounts and scheduled tasks.&lt;/strong&gt; Attackers commonly create a user to return through, and register a scheduled task that reinstalls the payload after you clean it. A site that keeps reinfecting on a regular cycle almost always has a scheduled task nobody looked for.&lt;/p&gt;




&lt;h2&gt;
  
  
  Why "Just Restore a Backup" Usually Fails
&lt;/h2&gt;

&lt;p&gt;It is the first suggestion everyone receives and it is right about a third of the time.&lt;/p&gt;

&lt;p&gt;Restoring works when you know the compromise date, have a backup from before it, and have identified and fixed the vulnerability. Without all three it fails predictably. Restore a backup from last week and you may be restoring a site that was already compromised two weeks ago and merely quiet. Restore without patching the vulnerable plugin and you have rebuilt the door you were locked out of.&lt;/p&gt;

&lt;p&gt;There is also the problem of what a restore costs you. On a store or a membership site, rolling back means losing every order, registration and comment since the backup. That is often unacceptable, which pushes you towards cleaning the live site rather than replacing it.&lt;/p&gt;

&lt;p&gt;The reliable approach is a rebuild rather than a restore. Install WordPress core fresh, install clean copies of every plugin and theme from their official sources rather than from the compromised site, and carry across only the uploads directory and the database — both inspected first. That guarantees the executable code is clean, which file-by-file cleaning never quite does.&lt;/p&gt;




&lt;h2&gt;
  
  
  Cleaning the Database
&lt;/h2&gt;

&lt;p&gt;The database is where incomplete cleanups leave things behind, because scanners concentrate on files.&lt;/p&gt;

&lt;p&gt;Injected content usually appears in post content as hidden links or iframes, in the options table where redirect scripts get stored, and in user metadata. Search for script tags, base64-encoded blocks and unfamiliar domains across the content and options tables.&lt;/p&gt;

&lt;p&gt;Check the users table by hand. Look at every account with administrator privileges and confirm you recognise each one, then check registration dates against your own records.&lt;/p&gt;

&lt;p&gt;Look at scheduled tasks, which in WordPress live in the options table. An entry pointing at a function you do not recognise is how a site reinfects itself on schedule long after the files were cleaned.&lt;/p&gt;

&lt;p&gt;Take particular care with anything encoded. Attackers obfuscate payloads specifically so a search for obvious strings misses them, so decode anything suspicious rather than assuming it is a legitimate plugin doing something clever.&lt;/p&gt;




&lt;h2&gt;
  
  
  Getting Unflagged and Recovering Rankings
&lt;/h2&gt;

&lt;p&gt;Cleaning the site is not the end, because the warnings persist until you ask for them to be reviewed.&lt;/p&gt;

&lt;p&gt;If Google has flagged the site, the security issues report in Search Console tells you what was detected and lets you request a review once you have fixed it. Only request the review after the site is genuinely clean, because a failed review lengthens the process.&lt;/p&gt;

&lt;p&gt;Check whether the domain has landed on blocklists used by browsers and email providers. Being clean is not enough on its own; each maintains its own list and its own removal process.&lt;/p&gt;

&lt;p&gt;Then look at the damage. Search visibility usually recovers once warnings are lifted, but a site that spent weeks serving spam pages may have had those pages indexed. Check for indexed URLs that were never yours, remove them, and confirm the clean versions are being crawled. Our &lt;a href="https://mecanik.dev/en/posts/website-security-audit-cost-mitigation-guide/" rel="noopener noreferrer"&gt;website security audit guide&lt;/a&gt; covers the verification steps in more detail.&lt;/p&gt;




&lt;h2&gt;
  
  
  What Professional Recovery Costs
&lt;/h2&gt;

&lt;p&gt;Prices reflect typical UK rates and vary with how long the compromise went unnoticed.&lt;/p&gt;

&lt;p&gt;A straightforward cleanup on a small site caught quickly, with a known cause, generally runs £400 to £1,200 and takes a day or two. This is the common case when someone notices within a week.&lt;/p&gt;

&lt;p&gt;A full incident response — log analysis to establish entry point and timeline, clean rebuild, database inspection, credential rotation, hardening and blocklist removal — typically runs £1,500 to £5,000. This is what a store or a site holding customer data should expect, because you also need to establish whether data was accessed.&lt;/p&gt;

&lt;p&gt;Sites compromised for months, or hosting several sites on the same account, cost more, because cross-contamination between sites on shared hosting is common and each one must be checked.&lt;/p&gt;

&lt;p&gt;If personal data may have been accessed, there are obligations beyond the technical cleanup. UK GDPR requires notifying the ICO within 72 hours of becoming aware of a qualifying breach, and that clock starts at awareness, not at cleanup. Take advice early rather than after you have finished tidying. Our guide to &lt;a href="https://mecanik.dev/en/posts/gdpr-technical-compliance-for-uk-developers-in-2026/" rel="noopener noreferrer"&gt;GDPR technical compliance&lt;/a&gt; covers the engineering side of that.&lt;/p&gt;




&lt;h2&gt;
  
  
  Making Sure It Does Not Happen Again
&lt;/h2&gt;

&lt;p&gt;Recovery without hardening just resets the clock.&lt;/p&gt;

&lt;p&gt;Update discipline is the whole game. The overwhelming majority of compromises exploit a vulnerability with a patch already available, so the fix is a routine that applies security releases promptly and a policy of removing anything unmaintained. Premium plugins with lapsed licences should be renewed or replaced, never left in place.&lt;/p&gt;

&lt;p&gt;Reduce what can execute. Nothing in the uploads directory should ever run as PHP, file editing from the admin interface should be disabled, and administrator accounts should be few and individually named.&lt;/p&gt;

&lt;p&gt;Add multi-factor authentication on every administrator account and rate-limit the login endpoint. Most credential attacks are automated and stop being viable the moment a second factor exists.&lt;/p&gt;

&lt;p&gt;Finally, back up properly and test it. A backup you have never restored is a hypothesis. Keep several generations, because the newest one may already contain the compromise. Our &lt;a href="https://mecanik.dev/en/posts/wordpress-security-hardening-checklist-2026/" rel="noopener noreferrer"&gt;WordPress security hardening checklist&lt;/a&gt; sets out the full configuration, and our &lt;a href="https://mecanik.dev/en/posts/wordpress-performance-audit-core-web-vitals/" rel="noopener noreferrer"&gt;WordPress performance audit guide&lt;/a&gt; covers the plugin discipline that reduces the attack surface as a side effect.&lt;/p&gt;




&lt;h2&gt;
  
  
  Get It Cleaned Properly
&lt;/h2&gt;

&lt;p&gt;Mecanik provides &lt;a href="https://mecanik.dev/en/wordpress-security-audit/" rel="noopener noreferrer"&gt;WordPress security audit&lt;/a&gt; and incident recovery work: establishing how the compromise happened, rebuilding cleanly rather than patching over it, inspecting the database, and hardening the site so the same route closes behind you.&lt;/p&gt;

&lt;p&gt;We work from the server logs rather than from a scanner's output, because a scanner tells you what it recognises and the logs tell you what actually happened. Where the site handles customer data we will also tell you plainly whether you appear to have a notifiable breach, rather than leaving you to discover that later. Ongoing maintenance is available through our &lt;a href="https://mecanik.dev/en/wordpress-developer-for-hire/" rel="noopener noreferrer"&gt;WordPress development service&lt;/a&gt;, which is generally cheaper than a second incident.&lt;/p&gt;

&lt;p&gt;If your site is compromised right now, take it offline, rotate the credentials, keep the logs, and get in touch.&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;Related reading:&lt;/strong&gt; &lt;a href="https://mecanik.dev/en/posts/api-security-protect-public-api/" rel="noopener noreferrer"&gt;API Security: How to Protect a Public API in 2026&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/owasp-top-10-explained-for-business-owners/" rel="noopener noreferrer"&gt;OWASP Top 10 Explained for Business Owners&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/server-security-audit-what-gets-checked/" rel="noopener noreferrer"&gt;Server Security Audit Checklist: What Actually Gets Checked&lt;/a&gt; and &lt;a href="https://mecanik.dev/en/posts/website-security-audit-for-uk-businesses-in-2026/" rel="noopener noreferrer"&gt;Website Security Audit Guide for UK Businesses in 2026&lt;/a&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  Frequently Asked Questions
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;What should I do first if my WordPress site is hacked?&lt;/strong&gt;&lt;br&gt;
Take the site offline, rotate every credential including hosting, database, FTP and all administrator accounts, and preserve a copy of the current files, database and server logs. Do not restore a backup or delete files yet, because that destroys the evidence needed to find the entry point.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Why does my WordPress site keep getting reinfected?&lt;/strong&gt;&lt;br&gt;
Almost always because the cleanup removed the malware but not the access. Look for administrator accounts you do not recognise, backdoors in the uploads directory, and scheduled tasks in the options table that reinstall the payload. Reinfection on a regular cycle usually indicates a scheduled task.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Can I just restore a backup to fix a hacked site?&lt;/strong&gt;&lt;br&gt;
Only if you know when the compromise happened, have a backup from before it, and have fixed the underlying vulnerability. Without all three you risk restoring an already-compromised site or reopening the same hole. A clean rebuild with fresh core, plugins and themes is more reliable.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;How much does WordPress malware removal cost?&lt;/strong&gt;&lt;br&gt;
A straightforward cleanup on a small site caught early typically costs £400 to £1,200. A full incident response with log analysis, clean rebuild, database inspection and hardening generally runs £1,500 to £5,000, and long-running or multi-site compromises cost more.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;How do I get my site unflagged by Google?&lt;/strong&gt;&lt;br&gt;
Clean the site fully, then request a review through the security issues report in Search Console. Only request it once the site is genuinely clean, since a failed review lengthens the process, and check separately for browser and email blocklists which each have their own removal procedure.&lt;/p&gt;

</description>
      <category>wordpress</category>
      <category>security</category>
      <category>cybersecurity</category>
    </item>
    <item>
      <title>WooCommerce Performance: Why Your Store Is Slow</title>
      <dc:creator>Mecanik1337</dc:creator>
      <pubDate>Sat, 03 Oct 2026 06:00:00 +0000</pubDate>
      <link>https://dev.to/mecanik-dev/woocommerce-performance-why-your-store-is-slow-38c</link>
      <guid>https://dev.to/mecanik-dev/woocommerce-performance-why-your-store-is-slow-38c</guid>
      <description>&lt;p&gt;Almost every WooCommerce performance investigation starts the same way. The store owner has already moved to a faster host, installed a caching plugin, and bought an image optimiser, and the site is still slow. They conclude that WooCommerce is simply heavy and give up.&lt;/p&gt;

&lt;p&gt;WooCommerce is heavier than a brochure site, which is unavoidable when every page can carry a cart. But a store that takes six seconds to load is not suffering from that overhead. It is suffering from something specific, and in my experience it is nearly always one of four things.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;The short version:&lt;/strong&gt; Shops are slow because cart and checkout pages cannot be page-cached, because the options table has grown enormous with autoloaded junk, because product queries scan an unindexed metadata table, and because thirty plugins each add their own scripts to every page. Hosting is the last thing to change, not the first.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  Why a Store Is Different From a Blog
&lt;/h2&gt;

&lt;p&gt;Understanding one distinction explains most WooCommerce performance behaviour.&lt;/p&gt;

&lt;p&gt;A blog post is the same for every visitor, so it can be generated once and served from cache to everyone. That is why brochure sites are fast almost regardless of how they are built. A store cannot do that on every page, because the cart is personal. The moment a visitor adds an item, the page has to reflect their state rather than a shared copy.&lt;/p&gt;

&lt;p&gt;The consequence is that cart, checkout and account pages bypass page caching entirely and execute PHP and database queries on every request. Those are also the pages where slowness costs you money directly. A slow category page loses browsers; a slow checkout loses buyers.&lt;/p&gt;

&lt;p&gt;So the useful question is never "is my site fast?" It is "how fast is my site for a logged-in visitor with something in their cart?" Test that state specifically, because it is the one your revenue depends on and the one every synthetic speed test misses.&lt;/p&gt;




&lt;h2&gt;
  
  
  The Four Things That Are Actually Wrong
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;An overloaded options table.&lt;/strong&gt; WordPress loads a set of options on every single request, and plugins add to it freely. Uninstalled plugins routinely leave their rows behind. On older stores this table grows to tens of megabytes of autoloaded data being read on every page view including the checkout. It is invisible, it is cumulative, and it is one of the highest-return fixes available. Check the total size of autoloaded options first; if it is measured in megabytes rather than kilobytes, you have found real time.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Product queries against unindexed metadata.&lt;/strong&gt; WooCommerce historically stored product attributes, prices and stock in a generic metadata table shared with everything else. Filtering or sorting a large catalogue means joining that table repeatedly. With a few hundred products nobody notices. With tens of thousands, category and filter pages slow to a crawl. Newer WooCommerce versions moved order data to dedicated tables specifically to relieve this pressure, and enabling that storage on a store with a long order history is usually worth doing on its own.&lt;/p&gt;

&lt;h3&gt;
  
  
  Plugins and External Calls
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Plugin sprawl on the critical path.&lt;/strong&gt; The problem is rarely the count itself; it is that most plugins enqueue their CSS and JavaScript on every page rather than only where needed. A booking plugin used on one page loads its assets on your checkout. The fix is unglamorous: audit what each plugin loads, dequeue assets outside their own pages, and remove anything whose function you cannot name.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Uncached third-party calls.&lt;/strong&gt; Live shipping rates, tax lookups, currency conversion and stock checks against an external system all place a network request inside the page load. When that provider is slow, your checkout is slow, and when it fails your checkout fails. Every external call in a request path needs a timeout, a cache and a fallback. Our guide to &lt;a href="https://mecanik.dev/en/posts/third-party-api-integration-cost-failure-modes/" rel="noopener noreferrer"&gt;third-party API integration&lt;/a&gt; covers how that should be built.&lt;/p&gt;




&lt;h2&gt;
  
  
  What Actually Helps, In Order
&lt;/h2&gt;

&lt;p&gt;Work through these in sequence, because each one changes what the next measurement tells you.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Object caching, not just page caching.&lt;/strong&gt; Page caching serves whole HTML pages and cannot help cart or checkout. A persistent object cache stores the results of database queries in memory and speeds up exactly the pages page caching cannot touch. For a store this is usually the single largest improvement available, and it is the step most often skipped because the caching plugin already installed gave the impression the job was done.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Database maintenance.&lt;/strong&gt; Clear expired transients, remove orphaned metadata from deleted products and orders, and trim post revisions. On a store that has been trading for years this routinely removes a large fraction of the database. Schedule it rather than doing it once.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Then hosting.&lt;/strong&gt; Once caching and the database are in order, hosting genuinely matters: PHP version, available memory, whether the database is on the same machine, and whether you are on shared hosting competing with other tenants. But moving host before fixing the above just relocates the problem to a more expensive address.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Assets last.&lt;/strong&gt; Image formats, lazy loading and script deferral are worth doing and they are what most guides lead with. They improve the loading experience of pages that were already being served reasonably quickly. They do very little for a checkout that spends four seconds in PHP before sending a byte.&lt;/p&gt;




&lt;h2&gt;
  
  
  Measuring WooCommerce Performance Properly
&lt;/h2&gt;

&lt;p&gt;Synthetic scores mislead store owners more than any other group, so measure deliberately.&lt;/p&gt;

&lt;p&gt;Test the logged-in, cart-populated state. Most tools test an anonymous visitor hitting the homepage, which is the fastest possible path through your site and tells you almost nothing about checkout.&lt;/p&gt;

&lt;p&gt;Separate server time from front-end time. If the server takes three seconds to produce the HTML, no amount of image optimisation will save the page. Time to first byte tells you which half of the problem you have, and therefore which of the fixes above applies.&lt;/p&gt;

&lt;p&gt;Use field data rather than lab data where you can. Real visitors on real connections and real phones produce a different picture from a test run in a data centre, and Core Web Vitals are assessed on the former. Our &lt;a href="https://mecanik.dev/en/posts/wordpress-performance-audit-core-web-vitals/" rel="noopener noreferrer"&gt;WordPress performance audit guide&lt;/a&gt; covers how to read those metrics properly, and &lt;a href="https://mecanik.dev/en/posts/core-web-vitals-2026-how-to-pass/" rel="noopener noreferrer"&gt;Core Web Vitals in 2026&lt;/a&gt; explains what the thresholds actually require.&lt;/p&gt;

&lt;p&gt;Finally, watch the database directly during a slow request. A query log showing the same query executed two hundred times on one page load identifies the culprit immediately, and that pattern is extremely common in stores running several plugins that each ask for product data independently.&lt;/p&gt;




&lt;h2&gt;
  
  
  What This Work Costs
&lt;/h2&gt;

&lt;p&gt;Prices below reflect typical UK agency rates for a store of moderate size.&lt;/p&gt;

&lt;p&gt;A performance audit that identifies the specific causes, with a prioritised fix list and before-and-after measurements, generally runs £900 to £2,500. That is a diagnostic engagement and it is worth buying separately, because it tells you whether the remaining work is a week or a month.&lt;/p&gt;

&lt;p&gt;Implementing the common fixes — object caching, database cleanup, plugin asset auditing, external call caching — usually runs £2,000 to £6,000 depending on how much has accumulated.&lt;/p&gt;

&lt;p&gt;Deeper work costs more because it is genuinely development. Migrating a large catalogue to indexed storage, rebuilding a filter system that scans metadata, or replacing a slow plugin with a targeted custom implementation typically falls between £6,000 and £20,000.&lt;/p&gt;

&lt;p&gt;The figure that matters more than any of these is what slowness costs you. Checkout abandonment rises measurably with load time, so a store turning over meaningful revenue can usually justify the audit on the checkout page alone.&lt;/p&gt;




&lt;h2&gt;
  
  
  Fix the Store, Not the Score
&lt;/h2&gt;

&lt;p&gt;Mecanik does WooCommerce performance work as part of our &lt;a href="https://mecanik.dev/en/wordpress-developer-for-hire/" rel="noopener noreferrer"&gt;WordPress development service&lt;/a&gt;, and we start by measuring the logged-in checkout path rather than the homepage, because that is where stores actually lose money.&lt;/p&gt;

&lt;p&gt;We look at autoloaded options, order storage, query patterns and external calls before recommending a host change, and we give you the measurements both before and after so the improvement is verifiable rather than asserted. If your store is slow because it has outgrown the platform rather than because it is misconfigured, we will tell you that too — our comparison of &lt;a href="https://mecanik.dev/en/posts/ecommerce-website-development-shopify-vs-custom-in-2026/" rel="noopener noreferrer"&gt;Shopify and custom ecommerce&lt;/a&gt; covers where that line sits.&lt;/p&gt;

&lt;p&gt;Send us the URL and roughly how many products and orders the store holds, and we will tell you which of the four causes above you are most likely facing.&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;Related reading:&lt;/strong&gt; &lt;a href="https://mecanik.dev/en/posts/wordpress-hacked-malware-removal-recovery/" rel="noopener noreferrer"&gt;WordPress Hacked: Malware Removal and Recovery Guide&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/scale-ecommerce-business-uk-tech-playbook/" rel="noopener noreferrer"&gt;How to Scale an E-commerce Business in the UK: 2026 Guide&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/hire-drupal-developer-rates-skills-vetting/" rel="noopener noreferrer"&gt;Hire a Drupal Developer: Rates, Skills and Vetting&lt;/a&gt; and &lt;a href="https://mecanik.dev/en/posts/how-much-does-a-website-cost-in-the-uk-in-2026/" rel="noopener noreferrer"&gt;How Much Does a Website Cost in the UK in 2026?&lt;/a&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  Frequently Asked Questions
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Why is my WooCommerce site slow even with a caching plugin?&lt;/strong&gt;&lt;br&gt;
Page caching cannot be applied to cart, checkout and account pages, because those must reflect each visitor's own state. Those pages execute PHP and database queries on every request, so speeding them up requires object caching and database work rather than page caching.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Does moving to better hosting fix WooCommerce performance?&lt;/strong&gt;&lt;br&gt;
Only partly, and it should not be the first step. If the options table is bloated, queries are unindexed and plugins load assets everywhere, better hosting makes the same problems slightly faster at higher cost. Fix caching and the database first, then reassess hosting.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;How many plugins are too many for WooCommerce?&lt;/strong&gt;&lt;br&gt;
The count matters less than what each one loads. Twenty well-behaved plugins that only enqueue assets on their own pages cause less harm than eight that load scripts site-wide. Audit what each adds to the checkout, and remove anything whose purpose nobody can state.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;What does WooCommerce speed optimisation cost?&lt;/strong&gt;&lt;br&gt;
A diagnostic audit with a prioritised fix list typically costs £900 to £2,500. Implementing common fixes such as object caching, database cleanup and asset auditing usually runs £2,000 to £6,000, while catalogue or filter rework can reach £6,000 to £20,000.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;How should I test WooCommerce performance properly?&lt;/strong&gt;&lt;br&gt;
Test as a logged-in visitor with items in the cart, not an anonymous homepage visit. Separate server response time from front-end rendering to see which half is slow, and use field data from real visitors rather than relying only on lab scores.&lt;/p&gt;

</description>
      <category>wordpress</category>
      <category>ecommerce</category>
      <category>performance</category>
      <category>webdev</category>
    </item>
    <item>
      <title>Penetration Testing Cost: 2026 Enterprise Budgeting Guide</title>
      <dc:creator>Mecanik1337</dc:creator>
      <pubDate>Fri, 02 Oct 2026 18:00:00 +0000</pubDate>
      <link>https://dev.to/mecanik-dev/penetration-testing-cost-2026-enterprise-budgeting-guide-44ih</link>
      <guid>https://dev.to/mecanik-dev/penetration-testing-cost-2026-enterprise-budgeting-guide-44ih</guid>
      <description>&lt;p&gt;Calculating the cost of penetration testing in the UK is a vital compliance task for enterprises planning cyber security audits in 2026. With business transactions shifting online, maintaining strict application security is critical to protect sensitive client databases and avoid expensive regulatory penalties. Commissioning an annual penetration test has shifted from a general recommendation to a standard requirement under local frameworks. This guide breaks down the pricing models, scope definitions, and compliance standards used to calculate penetration testing budgets.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Compliance Risk Warning:&lt;/strong&gt; Relying purely on automated vulnerability scanners does not constitute a penetration test. Under standard industry frameworks, automated tools fail to identify complex logic bugs, leaving your systems vulnerable to manual breaches.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Key Takeaways:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Costs vary based on IP count, active user roles, and network complexity.&lt;/li&gt;
&lt;li&gt;Small-scale web application pen tests range from £3,500 to £6,500, while complex enterprise networks start at £8,000.&lt;/li&gt;
&lt;li&gt;Working with CREST-accredited agencies is essential to pass compliance frameworks like ISO 27001 or PCI-DSS.&lt;/li&gt;
&lt;li&gt;Retaining a detailed vulnerability report simplifies structural remediation, saving engineering hours post-audit.&lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  Variables That Dictate Penetration Testing Cost
&lt;/h2&gt;

&lt;p&gt;A professional security audit requires manual validation by experienced ethical hackers. According to guidelines from the &lt;a href="https://www.ncsc.gov.uk/" rel="noopener noreferrer"&gt;National Cyber Security Centre (NCSC)&lt;/a&gt;, scoping security tests accurately is the first step to prevent budget overruns. Several parameters directly impact the scope of work and the final quote. Therefore, you must define the target surfaces cleanly to avoid budget creep.&lt;/p&gt;

&lt;h3&gt;
  
  
  1. Scope and Target Count
&lt;/h3&gt;

&lt;p&gt;The number of servers, external IP addresses, internal domains, and active APIs dictates the test duration. Additionally, a web application with multiple user access levels requires testing each authorisation path to identify privilege escalation risks.&lt;/p&gt;

&lt;h3&gt;
  
  
  2. Testing Methodology: Black vs. White Box
&lt;/h3&gt;

&lt;p&gt;The amount of information provided to the security engineers determines the testing path and, ultimately, the testing style.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Black-Box Testing:&lt;/strong&gt; Engineers receive only the target URL or IP. This method simulates an external attack, requiring more hours to gather intelligence and map endpoints.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;White-Box Testing:&lt;/strong&gt; Developers provide source code access, network diagrams, and database configurations. This allows for deep review but requires close collaboration.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  3. Compliance and Industry Requirements
&lt;/h3&gt;

&lt;p&gt;UK businesses bidding for public sector contracts or working in fintech must meet specific security baselines (such as Cyber Essentials Plus or PCI-DSS). To satisfy these audit criteria, the testing agency must run specialised tests, and this additional compliance layer increases testing hours and the final fee.&lt;/p&gt;




&lt;h2&gt;
  
  
  Average Penetration Testing Costs in the UK for 2026
&lt;/h2&gt;

&lt;p&gt;To help your compliance team budget, the following table details the average cost metrics for security audits in the UK:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Testing Target&lt;/th&gt;
&lt;th&gt;Average Cost Range (GBP)&lt;/th&gt;
&lt;th&gt;Recommended Testing Frequency&lt;/th&gt;
&lt;th&gt;Compliance Standards Met&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Simple Web App / API&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;£3,500 - £6,500&lt;/td&gt;
&lt;td&gt;Annual / Post-Update&lt;/td&gt;
&lt;td&gt;GDPR / OWASP Top 10&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Enterprise Network (Internal &amp;amp; External)&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;£8,000 - £15,000+&lt;/td&gt;
&lt;td&gt;Annual&lt;/td&gt;
&lt;td&gt;ISO 27001 / PCI-DSS&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Active Mobile Application (iOS &amp;amp; Android)&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;£5,000 - £10,000&lt;/td&gt;
&lt;td&gt;Annual&lt;/td&gt;
&lt;td&gt;OWASP MASVS&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Cloud Infrastructure (AWS/Cloudflare)&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;£6,000 - £12,000&lt;/td&gt;
&lt;td&gt;Annual / Major Change&lt;/td&gt;
&lt;td&gt;CIS Benchmarks&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;These estimates assume hiring a certified agency that provides comprehensive liability insurance and senior, accredited testers.&lt;/p&gt;




&lt;h2&gt;
  
  
  How a Pen-Test Quote Is Built: A Worked Example
&lt;/h2&gt;

&lt;p&gt;Most reputable UK consultancies price on a &lt;strong&gt;day-rate basis&lt;/strong&gt;. The quote is simply the estimated number of testing days multiplied by the consultant day rate, plus reporting and a retest. This makes the arithmetic easy to interrogate once you know the inputs. For CREST-registered testers, day rates typically sit between &lt;strong&gt;£1,000 and £1,500 per day&lt;/strong&gt; (illustrative for 2026); highly specialised work — bespoke thick-client, embedded, or hardware testing — commands more.&lt;/p&gt;

&lt;p&gt;Consider a realistic scenario: a mid-sized SaaS business commissioning its annual assessment. The in-scope assets are a customer-facing web application with three user roles, the REST API behind it, and a small external network perimeter. A blended senior rate of &lt;strong&gt;£1,200 per day&lt;/strong&gt; applies across the engagement.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Component&lt;/th&gt;
&lt;th&gt;Scope detail&lt;/th&gt;
&lt;th&gt;Estimated effort (days)&lt;/th&gt;
&lt;th&gt;Subtotal at £1,200/day&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Web application (authenticated)&lt;/td&gt;
&lt;td&gt;3 user roles, ~25 dynamic pages&lt;/td&gt;
&lt;td&gt;5.0&lt;/td&gt;
&lt;td&gt;£6,000&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;REST API&lt;/td&gt;
&lt;td&gt;~40 endpoints&lt;/td&gt;
&lt;td&gt;2.5&lt;/td&gt;
&lt;td&gt;£3,000&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;External network&lt;/td&gt;
&lt;td&gt;12 live IP addresses&lt;/td&gt;
&lt;td&gt;1.5&lt;/td&gt;
&lt;td&gt;£1,800&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Reporting &amp;amp; QA&lt;/td&gt;
&lt;td&gt;Findings write-up, executive summary, peer review&lt;/td&gt;
&lt;td&gt;1.5&lt;/td&gt;
&lt;td&gt;£1,800&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Remediation retest&lt;/td&gt;
&lt;td&gt;Verify critical and high-severity fixes&lt;/td&gt;
&lt;td&gt;1.0&lt;/td&gt;
&lt;td&gt;£1,200&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Total&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;—&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;11.5 days&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;£13,800&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;The headline figure of roughly &lt;strong&gt;£13,800&lt;/strong&gt; is therefore not a mysterious lump sum. It is 11.5 days of effort at a £1,200 blended rate. The day counts themselves come from a scoping questionnaire: the tester estimates hours per authorisation path, per endpoint cluster, and per network segment, then rounds to sensible half-days. Change any input and the price moves predictably. Add a native mobile application and you add roughly 4 to 6 days (£4,800–£7,200). Insist on a fully black-box engagement and reconnaissance alone can add a day or two, because the team must map from scratch what a white-box brief would have handed over.&lt;/p&gt;

&lt;p&gt;Most agencies present this as a &lt;strong&gt;fixed-price quote&lt;/strong&gt; rather than an open day rate, having converted their day estimate into a single figure. The practical difference matters at contract time: a fixed price protects you if the work runs long, but only against the scope you agreed, so anything discovered outside the original boundary becomes a change request. Always confirm what the quote assumes — the number of days baked in, whether one retest is included, and how out-of-scope findings are handled — before you sign. A supplier who cannot break their fixed price back down into days and rates is a supplier worth questioning.&lt;/p&gt;

&lt;h2&gt;
  
  
  What Makes Up the Headline Price: A Line-Item Breakdown
&lt;/h2&gt;

&lt;p&gt;Even within a single engagement, the fee covers far more than hands-on-keyboard exploitation. Understanding how the effort divides helps you compare quotes like for like and spot a supplier who has under-scoped the unglamorous stages.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Stage&lt;/th&gt;
&lt;th&gt;What it covers&lt;/th&gt;
&lt;th&gt;Typical share of effort&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Scoping &amp;amp; pre-engagement&lt;/td&gt;
&lt;td&gt;Questionnaire, rules of engagement, written authorisation&lt;/td&gt;
&lt;td&gt;5–10%&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Reconnaissance &amp;amp; mapping&lt;/td&gt;
&lt;td&gt;Enumerating the attack surface, cataloguing endpoints&lt;/td&gt;
&lt;td&gt;10–15%&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Active testing &amp;amp; exploitation&lt;/td&gt;
&lt;td&gt;Manual testing, chaining findings, privilege escalation&lt;/td&gt;
&lt;td&gt;45–55%&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Reporting &amp;amp; QA review&lt;/td&gt;
&lt;td&gt;Write-up, severity ratings, senior peer review&lt;/td&gt;
&lt;td&gt;20–25%&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Remediation retest&lt;/td&gt;
&lt;td&gt;Re-testing issues your team has patched&lt;/td&gt;
&lt;td&gt;5–10%&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;The reporting stage surprises many first-time buyers. A test that finds serious problems but documents them poorly is close to worthless: your engineers cannot reproduce or prioritise what they cannot understand. When you analyse two quotes and one is conspicuously cheaper, check whether it has quietly compressed reporting and retesting — that is usually where corners get cut.&lt;/p&gt;

&lt;h2&gt;
  
  
  Ongoing and Hidden Costs to Budget For
&lt;/h2&gt;

&lt;p&gt;The invoice from the testing agency is rarely the whole story. A realistic annual security budget should account for these recurring or easily overlooked items:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Remediation engineering time.&lt;/strong&gt; Fixing what the test finds is frequently the single largest cost, and it lands on your own team rather than the supplier's invoice. A report with a dozen medium and high findings can absorb several developer-weeks.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Annual re-testing.&lt;/strong&gt; Frameworks such as ISO 27001 and PCI-DSS expect a fresh assessment at least yearly, plus targeted testing after any major change.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Retest and validation fees.&lt;/strong&gt; Most engagements include one retest window; verifying fixes after that window has closed is usually billed separately.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Interim scanning and tooling.&lt;/strong&gt; Many organisations run authenticated vulnerability scanning between annual tests, which carries its own licence cost.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Internal staff time.&lt;/strong&gt; Scoping calls, environment preparation, and provisioning test accounts all consume hours that rarely appear in any quote.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;As an annual rule of thumb, plan for total security-testing spend of roughly &lt;strong&gt;1.5 to 2 times the headline test fee&lt;/strong&gt; once remediation labour, retests, and interim scanning are included (illustrative). In our worked example, the £13,800 engagement realistically implies a &lt;strong&gt;£20,000–£28,000&lt;/strong&gt; all-in annual figure for that programme of work.&lt;/p&gt;

&lt;h2&gt;
  
  
  What Moves the Price Up or Down
&lt;/h2&gt;

&lt;p&gt;Because the model is days multiplied by a rate, every price lever ultimately changes the day count. The factors below push a quote in one direction or the other:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Pushes it up:&lt;/strong&gt; a fully black-box brief, many user roles or authorisation boundaries, compliance overlays such as PCI-DSS or CBEST that mandate specific methodologies and evidence, out-of-hours testing to protect production, and any physical or social-engineering component.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Pulls it down:&lt;/strong&gt; a tightly defined and well-documented scope, white-box or grey-box access, consolidating several assets into one booking, a stable code freeze during the test window, and a standing retainer relationship that removes repeated scoping overhead.&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  Best Practices to Control Testing Expenses
&lt;/h2&gt;

&lt;p&gt;Protecting your budget from inflation requires preparing your systems before the audit begins. To keep costs under control, follow these optimisation guidelines:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Clean up Active Codebases:&lt;/strong&gt; Resolve obvious OWASP vulnerability points using automated scanners before the engineers start testing.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Establish Clear Scopes:&lt;/strong&gt; Exclude non-critical staging subdomains or legacy static servers from the target list to limit testing hours.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Verify Third-Party Approvals:&lt;/strong&gt; If your systems are hosted on managed servers, ensure you secure authorisation from the host to prevent testing blocks.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Link remediations to SLAs:&lt;/strong&gt; Ensure your engineering team is scheduled to patch identified vulnerabilities immediately upon receiving the draft report.&lt;/li&gt;
&lt;/ol&gt;




&lt;h2&gt;
  
  
  Partner with a Vetted UK Security Consultancy
&lt;/h2&gt;

&lt;p&gt;Understanding the elements that shape your budget ensures your compliance audits stay on schedule. Mecanik provides professional &lt;a href="https://mecanik.dev/en/penetration-testing-services/" rel="noopener noreferrer"&gt;penetration testing services&lt;/a&gt; and comprehensive security testing through the &lt;a href="https://mecanik.dev/en/website-security-audit/" rel="noopener noreferrer"&gt;website security audit&lt;/a&gt; page. We specialise in web application security, server hardening, and API compliance audits. Contact us today to schedule your scoping session.&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;Related reading:&lt;/strong&gt; &lt;a href="https://mecanik.dev/en/posts/website-security-audit-cost-mitigation-guide/" rel="noopener noreferrer"&gt;Website Security Audit: Prevent Enterprise Breaches&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/cyber-essentials-compliance-uk-guide/" rel="noopener noreferrer"&gt;Cyber Essentials Compliance: A UK Vetting Guide 2026&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/penetration-testing-uk-what-to-expect-in-2026/" rel="noopener noreferrer"&gt;Penetration Testing in the UK - What to Expect in 2026&lt;/a&gt; and &lt;a href="https://mecanik.dev/en/posts/types-of-penetration-testing-black-box-white-box-grey-box/" rel="noopener noreferrer"&gt;Types of Penetration Testing: Black, White and Grey Box&lt;/a&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  Frequently Asked Questions
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;What is the average penetration testing cost uk?&lt;/strong&gt;&lt;br&gt;
The average cost of a penetration test in the UK starts at £3,500 for a simple web application or API and can exceed £15,000 for complex enterprise networks. The final pricing depends on the number of IP addresses, active endpoints, user roles, and compliance requirements.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Why do I need a manual penetration test instead of a scanner?&lt;/strong&gt;&lt;br&gt;
Automated scanners only identify known signature patterns. Conversely, a manual penetration test uses ethical hackers to identify complex logic flaws, chain minor issues into critical breaches, and verify access escalation bugs that scanners cannot spot.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;How often should a UK business conduct a pen test?&lt;/strong&gt;&lt;br&gt;
UK businesses should conduct a penetration test at least once a year to maintain compliance standards like ISO 27001. Additionally, you should commission a pen test after launching major feature updates, changing database structures, or shifting cloud hosts.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;What is the role of CREST accreditation in pen testing?&lt;/strong&gt;&lt;br&gt;
CREST accreditation verifies that the security agency and its engineers follow strict technical, ethical, and legal guidelines. Hiring a CREST-approved firm is often a requirement to satisfy compliance audits and validate your security posture to enterprise clients.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;What happens if the pen test identifies critical vulnerabilities?&lt;/strong&gt;&lt;br&gt;
A professional test report categorises vulnerabilities by severity (Critical, High, Medium, Low). Your development team should patch critical and high risks immediately, and the testing agency should run a validation test to confirm the patches are secure.&lt;/p&gt;

</description>
      <category>security</category>
      <category>cybersecurity</category>
      <category>devops</category>
    </item>
    <item>
      <title>Core Web Vitals in 2026: How to Actually Pass</title>
      <dc:creator>Mecanik1337</dc:creator>
      <pubDate>Fri, 02 Oct 2026 06:00:00 +0000</pubDate>
      <link>https://dev.to/mecanik-dev/core-web-vitals-in-2026-how-to-actually-pass-2cm2</link>
      <guid>https://dev.to/mecanik-dev/core-web-vitals-in-2026-how-to-actually-pass-2cm2</guid>
      <description>&lt;p&gt;Core Web Vitals are Google's measurable signals for real-world page experience, and they feed into ranking. Passing them is not about chasing a green score for its own sake; it is about a site that loads fast, responds instantly, and does not jump around while people use it. This guide explains the three metrics as they stand in 2026 and, more importantly, the fixes that actually move each one.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;TL;DR&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The three Core Web Vitals are LCP (loading), INP (responsiveness), and CLS (visual stability). INP replaced FID as a Core Web Vital in 2024&lt;/li&gt;
&lt;li&gt;"Good" thresholds: LCP under 2.5s, INP under 200ms, CLS under 0.1, measured at the 75th percentile of real visits&lt;/li&gt;
&lt;li&gt;The highest-impact fixes are optimising the largest image or text block, reducing and breaking up JavaScript, and reserving space for images, ads, and embeds&lt;/li&gt;
&lt;li&gt;Use field data (real users), not just lab tests, because Google ranks on real-world performance&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  The Three Core Web Vitals (2026)
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Largest Contentful Paint (LCP): Loading
&lt;/h3&gt;

&lt;p&gt;LCP measures how long it takes for the largest visible element (usually a hero image, banner, or large text block) to render. &lt;strong&gt;Good: under 2.5 seconds.&lt;/strong&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Interaction to Next Paint (INP): Responsiveness
&lt;/h3&gt;

&lt;p&gt;INP measures how quickly the page responds to user interactions across the whole visit, replacing the older First Input Delay (FID) metric in 2024. It captures the delay between a tap or click and the next visual update. &lt;strong&gt;Good: under 200 milliseconds.&lt;/strong&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Cumulative Layout Shift (CLS): Visual Stability
&lt;/h3&gt;

&lt;p&gt;CLS measures how much the page unexpectedly shifts while loading (the frustrating jump when a late image or ad pushes content down). &lt;strong&gt;Good: under 0.1.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Google evaluates these at the &lt;strong&gt;75th percentile&lt;/strong&gt; of real visits, so you need most of your users, not just the fastest, to have a good experience.&lt;/p&gt;

&lt;h2&gt;
  
  
  Fixing LCP
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Optimise the LCP element.&lt;/strong&gt; Identify it (most tools name it) and make it load fast: compress and correctly size the image, serve modern formats (WebP/AVIF), and avoid lazy-loading the hero image.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Serve responsive images&lt;/strong&gt; with a proper &lt;code&gt;srcset&lt;/code&gt; so devices download an appropriately sized file rather than a huge one. (See the guide to &lt;a href="https://mecanik.dev/en/posts/how-to-deal-with-responsive-images/" rel="noopener noreferrer"&gt;dealing with responsive images&lt;/a&gt;.)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Speed up the server response&lt;/strong&gt; (TTFB) with caching and a CDN so the document arrives quickly.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Preload critical resources&lt;/strong&gt; (the LCP image, key fonts) and eliminate render-blocking CSS and JavaScript where possible.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Use a fast image pipeline.&lt;/strong&gt; Serving images through an optimised service like &lt;a href="https://mecanik.dev/en/posts/cloudflare-image-transformations-resize-and-optimize-on-the-fly/" rel="noopener noreferrer"&gt;Cloudflare image transformations&lt;/a&gt; resizes and compresses on the fly.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Fixing INP
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Reduce JavaScript execution.&lt;/strong&gt; Heavy scripts block the main thread and delay responses. Ship less JavaScript and remove unused code.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Break up long tasks.&lt;/strong&gt; Split long-running work so the browser can respond to input between chunks.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Defer non-critical work&lt;/strong&gt; until after interaction, and avoid large, synchronous handlers.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Audit third-party scripts.&lt;/strong&gt; Tag managers, chat widgets, and analytics are common INP culprits; load them efficiently or remove what you do not need.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Fixing CLS
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Always set width and height&lt;/strong&gt; (or CSS &lt;code&gt;aspect-ratio&lt;/code&gt;) on images and video so the browser reserves space.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Reserve space for ads, embeds, and iframes&lt;/strong&gt; so they do not push content when they load.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Avoid inserting content above existing content&lt;/strong&gt; after load.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Preload fonts and use &lt;code&gt;font-display&lt;/code&gt; sensibly&lt;/strong&gt; to reduce layout shift from late-loading fonts.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Measure the Right Way
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Field data over lab data.&lt;/strong&gt; Google ranks on real-user (field) data such as the &lt;a href="https://developer.chrome.com/docs/crux" rel="noopener noreferrer"&gt;Chrome User Experience Report&lt;/a&gt;, not just a single lab run. A perfect lab score with poor field data will not pass.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Watch the 75th percentile.&lt;/strong&gt; Improving your median is not enough; the slower quarter of visits is what fails you.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Test on real devices and connections,&lt;/strong&gt; especially mid-range mobile, not just a fast desktop.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Key Takeaways
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;The three Core Web Vitals in 2026 are LCP, INP (which replaced FID), and CLS.&lt;/li&gt;
&lt;li&gt;Aim for LCP under 2.5s, INP under 200ms, and CLS under 0.1 at the 75th percentile of real visits.&lt;/li&gt;
&lt;li&gt;The biggest wins: optimise the LCP element and images, cut and split JavaScript for INP, and reserve space to stop layout shift for CLS.&lt;/li&gt;
&lt;li&gt;Judge success on field data, not just a lab score.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Get a Professional Assessment
&lt;/h2&gt;

&lt;p&gt;Core Web Vitals are one part of technical SEO. A &lt;a href="https://mecanik.dev/en/technical-seo-audit/" rel="noopener noreferrer"&gt;technical SEO audit&lt;/a&gt; covers Core Web Vitals alongside crawl budget, indexation, site architecture, JavaScript rendering, and structured data, with a prioritised action plan based on real ranking impact. If speed is your main concern, the guide to &lt;a href="https://mecanik.dev/en/posts/speed-up-your-website-with-cloudflare/" rel="noopener noreferrer"&gt;speeding up your website with Cloudflare&lt;/a&gt; goes deeper on performance.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Related reading:&lt;/strong&gt; &lt;a href="https://mecanik.dev/en/posts/technical-seo-audit-cost-deliverables-pricing/" rel="noopener noreferrer"&gt;Technical SEO Audit Cost: 2026 Price and Deliverables Guide&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/wordpress-performance-audit-core-web-vitals/" rel="noopener noreferrer"&gt;WordPress Performance Audit: Pass Mobile Vitals Guide&lt;/a&gt;, &lt;a href="https://mecanik.dev/en/posts/cloudflare-cdn-caching-core-web-vitals/" rel="noopener noreferrer"&gt;Optimizing Cloudflare CDN Caching Strategy for Speed&lt;/a&gt; and &lt;a href="https://mecanik.dev/en/posts/website-redesign-uk-when-and-how-in-2026/" rel="noopener noreferrer"&gt;Website Redesign UK - When and How in 2026&lt;/a&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  Frequently Asked Questions (FAQ)
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;What are the three Core Web Vitals in 2026?&lt;/strong&gt;&lt;br&gt;
Largest Contentful Paint (LCP) for loading, Interaction to Next Paint (INP) for responsiveness, and Cumulative Layout Shift (CLS) for visual stability. INP replaced First Input Delay (FID) as a Core Web Vital in 2024.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;What are good Core Web Vitals scores?&lt;/strong&gt;&lt;br&gt;
LCP under 2.5 seconds, INP under 200 milliseconds, and CLS under 0.1, measured at the 75th percentile of real user visits. You need most visitors, not just the fastest, to hit these.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Do Core Web Vitals affect Google rankings?&lt;/strong&gt;&lt;br&gt;
Yes. They are part of Google's page experience signals. They are not the only or the strongest ranking factor, but for competitive queries a good page experience is a meaningful advantage, and a bad one holds you back.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Why does my site pass in the lab but fail in Search Console?&lt;/strong&gt;&lt;br&gt;
Because Google uses field data from real users, not a single lab test. Real devices, connections, and the 75th percentile expose problems a fast test machine hides. Optimise for real-world conditions.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;What is the fastest way to improve Core Web Vitals?&lt;/strong&gt;&lt;br&gt;
Usually optimising the LCP element (compress and size the largest image, avoid lazy-loading it) and reducing JavaScript. For CLS, set dimensions on images and reserve space for ads and embeds.&lt;/p&gt;

</description>
      <category>performance</category>
      <category>seo</category>
      <category>webdev</category>
    </item>
  </channel>
</rss>
