• Pl chevron_right

      JMP: Mitigating MITMs in XMPP

      news.movim.eu / PlanetJabber • 5 June 2025 • 5 minutes

    In October 2023, Jabber.ru, “the largest Russian XMPP messaging service”, discovered that both Hetzner and Linode had been targeting them with Machine-In-The-Middle (MITM) attacks for up to 6 months. MITM attacks are when an unauthorised third party intercepts traffic intended for someone else. At the point of interception, the attacker can inspect and even modify that traffic. TLS was created to mitigate this; all communication between the two parties is encrypted, so the third party sees nothing but gibberish (ciphertext).

    TLS is great, but it’s actually not enough when the attacker owns your network, as in Jabber.ru’s situation. Jabber.ru rented servers from Hetzner and Linode, who altered their network’s routing setup to obtain TLS certificates for Jabber.ru’s domains and successfully carry out a MITM. When connecting to an XMPP server, most clients are only configured to look for a valid certificate. A valid certificate matches the service’s domain name, is not expired, and is authorised by a known and trusted Certificate Authority (CA). If the client sees a certificate that’s signed by an unknown CA or whose expiry has passed or the domain in the cert doesn’t match the service domain or any combination of the those, it’s considered invalid; the client should terminate the connection before transmitting sensitive data, such as the user’s password.

    Because Hetzner and Linode controlled Jabber.ru’s network, they were able to meet all of those conditions. XMPP clients would just accept the rogue (but valid!) certificates and continue along as normal, unaware that they were actually connecting to a rogue server that forwarded their traffic (possibly with modifications) to the proper server.

    A fairly straightforward mitigation involves DNS-based Authentication of Named Entities, or DANE. This is just a standard way to securely communicate to clients what certificate keys they should expect when connecting. When clients initiate a connection to the XMPP server, they receive a TLS certificate that includes a public key. If the server admin has implemented DANE, the client can verify that the public key they received matches what the server administrator said they should receive. If they don’t match, the client should terminate the connection before transmitting sensitive data.

    Please note that while this post continually refers to DANE as it relates to XMPP, it could just as easily refer to any system that uses TLS, such as SMTP, Matrix, Mattermost, Rocket Chat, and more. The servers don’t need to do anything with DANE, just the clients connecting to the servers.

    Additionally note that this doesn’t mitigate cases where a provider has access to the server’s filesystem. If it’s a VPS, the provider could just snapshot the virtual disk and pick out the certificate files (as well as any other files they find interesting). If it’s a baremetal server, they’d have a harder time interacting with the filesystem without notifying the owner of their presence, but they could definitely still do it. Physical access is equivalent to root access.

    DANE requires the XMPP server’s authoritative nameserver, TLD, and domain registrar to all support DNSSEC. If those prerequisites are met, implementing DANE involves hashing the public keys of the current certificates and publishing them to DNS as TLSA records. The following commands extract the public key from a local PEM-encoded x509 certificate, re-encode it to DER, then hash it and print the hash.

    $ openssl x509 -in xmppserver.example.pem -inform pem -pubkey -noout \
      2>/dev/null | openssl ec -pubin -outform der 2>/dev/null | sha256sum \
      | awk '{print $1}
    
    9ff8a6d7aab386dfbd8272022d04f82204d1093332e6fc33d1c55ee21e0aedd0

    The long sequence of letters and numbers is the hash of the key and what gets published to DNS. The following commands initiate a connection to retrieve the certificates, extract and convert the public key, then hash it and print the hash.

    $ echo | openssl s_client -showcerts -servername xmppserver.example \
      -connect 198.51.100.7:5270 2>/dev/null | openssl x509 -inform pem \
      -pubkey -noout 2>/dev/null | openssl ec -pubin -outform der \
      2>/dev/null | sha256sum | awk '{print $1}'
    
    9ff8a6d7aab386dfbd8272022d04f82204d1093332e6fc33d1c55ee21e0aedd0

    When it comes to rotating certificates, admins have two options. The first and easiest is to reuse the key-pair from the original certificate. Certbot allows you to do this with the –reuse-key option. Caddy has an equivalent option. The other route is rotating both the certificates and the key-pair. This should be done well before the certificates expire. After obtaining the new certificates and keys, do not immediately swap them into production! Hash the new keys, then publish them as new TLSA records. Wait at least two TTLs, then swap the new certificates in and replace the old ones. Wait at least two more TTLs, then remove the TLSA records corresponding to the old key-pair.

    Waiting in between steps is necessary to reduce false positives and mitigate race conditions. Say the TTL is two hours and a client connects half an hour before the administrator starts rotating things. They obtain the new keys, hash them, publish the hashes, then swap the certificates and reload the XMPP server. Say the client reconnects five minutes after the administrator finishes. It’ll receive the new certificate file, but not pick up on the new record because administrator has said, through the two-hour TTL, that resolvers should only request DNS records once every two hours. For the next 1h25m, until the cache expires and their resolver re-requests all the TLSA records, the client will refuse to connect to the server and might even warn the user that the server and their account are compromised. Waiting two more TTLs before removing the old record is necessary to handle the very unlikely event where the client connects and receives the old certificate file right before the admin removes the old record. If they check DNS for that old, now-missing record after receiving the old certificate, the client should refuse the connection.

    danectl is a tool that uses Certbot to create and manage certificates and key-pairs, it generates BIND9 DNS records you can copy/paste into your DNS management tool, and even verifies that you’ve published the records correctly. It also works with SSHFP records to implement DANE with SSH servers, OPENPGPKEY records for GPG keys, and SMIMEA records for S/MIME certificates.

    Some clients are currently unaware of DANE, so it can be helpful to monitor TLS setups through an external service. Later in 2023, we created and announced a tool to fill this gap, CertWatch . You provide your XMPP server’s domain and it performs the same checks a client would over Tor, to prevent easy detection by an attacker.

    • Pl chevron_right

      JMP: Mitigating MITMs in XMPP

      news.movim.eu / PlanetJabber • 5 June 2025 • 5 minutes

    In October 2023, Jabber.ru, “the largest Russian XMPP messaging service”, discovered that both Hetzner and Linode had been targeting them with Machine-In-The-Middle (MITM) attacks for up to 6 months. MITM attacks are when an unauthorised third party intercepts traffic intended for someone else. At the point of interception, the attacker can inspect and even modify that traffic. TLS was created to mitigate this; all communication between the two parties is encrypted, so the third party sees nothing but gibberish (ciphertext).

    TLS is great, but it’s actually not enough when the attacker owns your network, as in Jabber.ru’s situation. Jabber.ru rented servers from Hetzner and Linode, who altered their network’s routing setup to obtain TLS certificates for Jabber.ru’s domains and successfully carry out a MITM. When connecting to an XMPP server, most clients are only configured to look for a valid certificate. A valid certificate matches the service’s domain name, is not expired, and is authorised by a known and trusted Certificate Authority (CA). If the client sees a certificate that’s signed by an unknown CA or whose expiry has passed or the domain in the cert doesn’t match the service domain or any combination of the those, it’s considered invalid; the client should terminate the connection before transmitting sensitive data, such as the user’s password.

    Because Hetzner and Linode controlled Jabber.ru’s network, they were able to meet all of those conditions. XMPP clients would just accept the rogue (but valid!) certificates and continue along as normal, unaware that they were actually connecting to a rogue server that forwarded their traffic (possibly with modifications) to the proper server.

    A fairly straightforward mitigation involves DNS-based Authentication of Named Entities, or DANE. This is just a standard way to securely communicate to clients what certificate keys they should expect when connecting. When clients initiate a connection to the XMPP server, they receive a TLS certificate that includes a public key. If the server admin has implemented DANE, the client can verify that the public key they received matches what the server administrator said they should receive. If they don’t match, the client should terminate the connection before transmitting sensitive data.

    Please note that while this post continually refers to DANE as it relates to XMPP, it could just as easily refer to any system that uses TLS, such as SMTP, Matrix, Mattermost, Rocket Chat, and more. The servers don’t need to do anything with DANE, just the clients connecting to the servers.

    Additionally note that this doesn’t mitigate cases where a provider has access to the server’s filesystem. If it’s a VPS, the provider could just snapshot the virtual disk and pick out the certificate files (as well as any other files they find interesting). If it’s a baremetal server, they’d have a harder time interacting with the filesystem without notifying the owner of their presence, but they could definitely still do it. Physical access is equivalent to root access.

    DANE requires the XMPP server’s authoritative nameserver, TLD, and domain registrar to all support DNSSEC. If those prerequisites are met, implementing DANE involves hashing the public keys of the current certificates and publishing them to DNS as TLSA records. The following commands extract the public key from a local PEM-encoded x509 certificate, re-encode it to DER, then hash it and print the hash.

    $ openssl x509 -in xmppserver.example.pem -inform pem -pubkey -noout \
      2>/dev/null | openssl ec -pubin -outform der 2>/dev/null | sha256sum \
      | awk '{print $1}
    
    9ff8a6d7aab386dfbd8272022d04f82204d1093332e6fc33d1c55ee21e0aedd0

    The long sequence of letters and numbers is the hash of the key and what gets published to DNS. The following commands initiate a connection to retrieve the certificates, extract and convert the public key, then hash it and print the hash.

    $ echo | openssl s_client -showcerts -servername xmppserver.example \
      -connect 198.51.100.7:5270 2>/dev/null | openssl x509 -inform pem \
      -pubkey -noout 2>/dev/null | openssl ec -pubin -outform der \
      2>/dev/null | sha256sum | awk '{print $1}'
    
    9ff8a6d7aab386dfbd8272022d04f82204d1093332e6fc33d1c55ee21e0aedd0

    When it comes to rotating certificates, admins have two options. The first and easiest is to reuse the key-pair from the original certificate. Certbot allows you to do this with the –reuse-key option. Caddy has an equivalent option. The other route is rotating both the certificates and the key-pair. This should be done well before the certificates expire. After obtaining the new certificates and keys, do not immediately swap them into production! Hash the new keys, then publish them as new TLSA records. Wait at least two TTLs, then swap the new certificates in and replace the old ones. Wait at least two more TTLs, then remove the TLSA records corresponding to the old key-pair.

    Waiting in between steps is necessary to reduce false positives and mitigate race conditions. Say the TTL is two hours and a client connects half an hour before the administrator starts rotating things. They obtain the new keys, hash them, publish the hashes, then swap the certificates and reload the XMPP server. Say the client reconnects five minutes after the administrator finishes. It’ll receive the new certificate file, but not pick up on the new record because administrator has said, through the two-hour TTL, that resolvers should only request DNS records once every two hours. For the next 1h25m, until the cache expires and their resolver re-requests all the TLSA records, the client will refuse to connect to the server and might even warn the user that the server and their account are compromised. Waiting two more TTLs before removing the old record is necessary to handle the very unlikely event where the client connects and receives the old certificate file right before the admin removes the old record. If they check DNS for that old, now-missing record after receiving the old certificate, the client should refuse the connection.

    danectl is a tool that uses Certbot to create and manage certificates and key-pairs, it generates BIND9 DNS records you can copy/paste into your DNS management tool, and even verifies that you’ve published the records correctly. It also works with SSHFP records to implement DANE with SSH servers, OPENPGPKEY records for GPG keys, and SMIMEA records for S/MIME certificates.

    Some clients are currently unaware of DANE, so it can be helpful to monitor TLS setups through an external service. Later in 2023, we created and announced a tool to fill this gap, CertWatch . You provide your XMPP server’s domain and it performs the same checks a client would over Tor, to prevent easy detection by an attacker.

    • Pl chevron_right

      JMP: Mitigating MITMs in XMPP

      news.movim.eu / PlanetJabber • 5 June 2025 • 5 minutes

    In October 2023, Jabber.ru, “the largest Russian XMPP messaging service”, discovered that both Hetzner and Linode had been targeting them with Machine-In-The-Middle (MITM) attacks for up to 6 months. MITM attacks are when an unauthorised third party intercepts traffic intended for someone else. At the point of interception, the attacker can inspect and even modify that traffic. TLS was created to mitigate this; all communication between the two parties is encrypted, so the third party sees nothing but gibberish (ciphertext).

    TLS is great, but it’s actually not enough when the attacker owns your network, as in Jabber.ru’s situation. Jabber.ru rented servers from Hetzner and Linode, who altered their network’s routing setup to obtain TLS certificates for Jabber.ru’s domains and successfully carry out a MITM. When connecting to an XMPP server, most clients are only configured to look for a valid certificate. A valid certificate matches the service’s domain name, is not expired, and is authorised by a known and trusted Certificate Authority (CA). If the client sees a certificate that’s signed by an unknown CA or whose expiry has passed or the domain in the cert doesn’t match the service domain or any combination of the those, it’s considered invalid; the client should terminate the connection before transmitting sensitive data, such as the user’s password.

    Because Hetzner and Linode controlled Jabber.ru’s network, they were able to meet all of those conditions. XMPP clients would just accept the rogue (but valid!) certificates and continue along as normal, unaware that they were actually connecting to a rogue server that forwarded their traffic (possibly with modifications) to the proper server.

    A fairly straightforward mitigation involves DNS-based Authentication of Named Entities, or DANE. This is just a standard way to securely communicate to clients what certificate keys they should expect when connecting. When clients initiate a connection to the XMPP server, they receive a TLS certificate that includes a public key. If the server admin has implemented DANE, the client can verify that the public key they received matches what the server administrator said they should receive. If they don’t match, the client should terminate the connection before transmitting sensitive data.

    Please note that while this post continually refers to DANE as it relates to XMPP, it could just as easily refer to any system that uses TLS, such as SMTP, Matrix, Mattermost, Rocket Chat, and more. The servers don’t need to do anything with DANE, just the clients connecting to the servers.

    Additionally note that this doesn’t mitigate cases where a provider has access to the server’s filesystem. If it’s a VPS, the provider could just snapshot the virtual disk and pick out the certificate files (as well as any other files they find interesting). If it’s a baremetal server, they’d have a harder time interacting with the filesystem without notifying the owner of their presence, but they could definitely still do it. Physical access is equivalent to root access.

    DANE requires the XMPP server’s authoritative nameserver, TLD, and domain registrar to all support DNSSEC. If those prerequisites are met, implementing DANE involves hashing the public keys of the current certificates and publishing them to DNS as TLSA records. The following commands extract the public key from a local PEM-encoded x509 certificate, re-encode it to DER, then hash it and print the hash.

    $ openssl x509 -in xmppserver.example.pem -inform pem -pubkey -noout \
      2>/dev/null | openssl ec -pubin -outform der 2>/dev/null | sha256sum \
      | awk '{print $1}
    
    9ff8a6d7aab386dfbd8272022d04f82204d1093332e6fc33d1c55ee21e0aedd0

    The long sequence of letters and numbers is the hash of the key and what gets published to DNS. The following commands initiate a connection to retrieve the certificates, extract and convert the public key, then hash it and print the hash.

    $ echo | openssl s_client -showcerts -servername xmppserver.example \
      -connect 198.51.100.7:5270 2>/dev/null | openssl x509 -inform pem \
      -pubkey -noout 2>/dev/null | openssl ec -pubin -outform der \
      2>/dev/null | sha256sum | awk '{print $1}'
    
    9ff8a6d7aab386dfbd8272022d04f82204d1093332e6fc33d1c55ee21e0aedd0

    When it comes to rotating certificates, admins have two options. The first and easiest is to reuse the key-pair from the original certificate. Certbot allows you to do this with the –reuse-key option. Caddy has an equivalent option. The other route is rotating both the certificates and the key-pair. This should be done well before the certificates expire. After obtaining the new certificates and keys, do not immediately swap them into production! Hash the new keys, then publish them as new TLSA records. Wait at least two TTLs, then swap the new certificates in and replace the old ones. Wait at least two more TTLs, then remove the TLSA records corresponding to the old key-pair.

    Waiting in between steps is necessary to reduce false positives and mitigate race conditions. Say the TTL is two hours and a client connects half an hour before the administrator starts rotating things. They obtain the new keys, hash them, publish the hashes, then swap the certificates and reload the XMPP server. Say the client reconnects five minutes after the administrator finishes. It’ll receive the new certificate file, but not pick up on the new record because administrator has said, through the two-hour TTL, that resolvers should only request DNS records once every two hours. For the next 1h25m, until the cache expires and their resolver re-requests all the TLSA records, the client will refuse to connect to the server and might even warn the user that the server and their account are compromised. Waiting two more TTLs before removing the old record is necessary to handle the very unlikely event where the client connects and receives the old certificate file right before the admin removes the old record. If they check DNS for that old, now-missing record after receiving the old certificate, the client should refuse the connection.

    danectl is a tool that uses Certbot to create and manage certificates and key-pairs, it generates BIND9 DNS records you can copy/paste into your DNS management tool, and even verifies that you’ve published the records correctly. It also works with SSHFP records to implement DANE with SSH servers, OPENPGPKEY records for GPG keys, and SMIMEA records for S/MIME certificates.

    Some clients are currently unaware of DANE, so it can be helpful to monitor TLS setups through an external service. Later in 2023, we created and announced a tool to fill this gap, CertWatch . You provide your XMPP server’s domain and it performs the same checks a client would over Tor, to prevent easy detection by an attacker.

    • Pl chevron_right

      Erlang Solutions: Avoiding Common Startup Tech Mistakes

      news.movim.eu / PlanetJabber • 5 June 2025 • 7 minutes

    When you’re moving quickly in a startup, taking shortcuts in your tech stack is tempting. A quick workaround here, a temporary fix there, with plans to tidy it all up later. But later can easily turn into never.

    Those early decisions, however small they seem, have a habit of sticking around. Over time, they slow you down, create technical debt, and make it harder to scale.

    This blog looks at how to avoid common startup tech mistakes by making smarter choices early on. You don’t need to build the perfect system from day one, but you do need to build something you won’t regret.

    The risks of rushing your tech stack decisions

    Your tech stack is the foundation of your product. Making quick choices to just keep things often comes with hidden costs.

    Common examples of early tech shortcuts

    • Choosing tools based on ease rather than long-term fit
    • Using third-party services without proper integration planning
    • Avoiding proper system design to save time
    • Stacking too many frameworks or libraries to plug gaps quickly
    • Skipping documentation, testing, or version control in the name of speed

    What could go wrong?

    Here are some of the common risks that come with rushing tech stack choices:

    Risk Impact
    Technical debt Every short-term choice adds friction later. Over time, progress slows as the team spends more time managing issues than delivering value.
    Security gaps Fast fixes can lead to poorly secured systems, especially when sensitive data is involved or best practices are skipped.
    Fragile foundations A patchwork stack becomes hard to maintain, debug, or scale, and onboarding new developers becomes a headache.
    Scaling problems Systems built for “now” can’t always support growth. Quick fixes often ignore load handling, resulting in slowdowns or breakdowns at scale.
    Innovation slowdown When all your energy goes into fixing past decisions, there’s little room left for building what’s next.

    The business cost of technical shortcuts

    They directly impact a startup’s ability to grow. From wasted dev time to lost customer trust, the cost of early shortcuts adds up fast. That’s not the kind of overhead most startups can afford.

    The long-term cost of technical debt

    We touched on technical debt earlier as one of the key risks of rushing early tech decisions. Now let’s look at it more closely, because for many startups, it’s the most persistent and costly issue that comes from cutting corners.

    Technical debt is the build-up of compromises made during development, from skipping tests and rushing features to patching bugs without addressing their root cause. These short-term choices eventually slow everything down, making it harder and more expensive to move forward.

    Let’s break down the long-term impact:

    The hidden costs of technical debt

    Consequence What it means
    Slower development Developers spend more time fixing old issues than building new features, reducing overall velocity.
    More bugs, more fire-fighting Poorly maintained code leads to more frequent and severe bugs, increasing customer support and downtime.
    Low team morale Constantly dealing with messy code creates frustration and burnout, which can hurt retention.
    Harder to scale As the product grows, tech debt makes it harder to add new features or pivot without causing breakages.
    Security risks Outdated code or rushed fixes often introduce vulnerabilities that can be exploited later.
    Increased costs Fixing problems later is far more expensive, both in time and budget.

    A Stripe report found developers spend up to 42% of their week handling technical debt. CIO research suggests 20–40% of IT budgets are spent addressing it.

    When it gets out of control

    Technical debt can halt progress entirely. We’ve seen startups and scale-ups locked into outdated or fragmented systems, where maintaining or updating anything becomes nearly impossible.

    Here are a few real-world scenarios:

    • Legacy overload : Systems running well past their intended lifespan, no longer supported or secure.
    • Integration failure : Poorly connected tools and services that don’t talk to each other, slowing everything down.
    • Scaling bottlenecks : Infrastructure so rigid that every new feature or user pushes it closer to breaking point.

    Security crises : Outdated code with known vulnerabilities, eventually forcing a full rebuild after a breach.

    What startups can do about it:

    You can’t avoid technical debt entirely, but you can manage it by:

    • Prioritising clean, maintainable code from day one
    • Setting time aside for refactoring and testing
    • Regularly reviewing architecture decisions
    • Choosing tools that support long-term scalability, not just quick wins

    Startups that manage technical debt proactively stay more adaptable, secure, and focused on building the future.

    Why scalability matters from day one

    Tech built in a rush might work for an MVP (minimum viable product), but without scalability and maintainability in mind, it becomes a liability, something we cover in more detail in our post on common MVP mistakes.

    60% of startups face major scalability issues within their first three years (McKinsey) . These problems aren’t just technical; they slow growth, frustrate users, and drain time and resources.

    Here’s why it’s critical to get it right from the start:

    1. Scaling later is harder and more expensive

    Retrofitting scalability into an existing product or tech is rarely clean. The cost (in both time and money) often outweighs what it would’ve taken to plan it earlier.

    2. Maintainable code accelerates growth

    Clean, modular code helps teams ship faster, fix bugs quicker, and onboard new engineers smoothly. Poor code slows everything down.

    3. Users don’t tolerate failure

    Unscalable systems break under pressure, which is exactly when users start showing up. That erodes trust, kills momentum, and makes customer retention harder.

    4. Bad tech choices can limit your future

    Tech that isn’t built to adapt can lock you into tools, vendors, or architectures that no longer serve your goals. That makes pivots and product evolution harder.

    Early-stage teams often defer these decisions to “later.” But in startups, later usually means too late . Thoughtful, scalable, and maintainable tech choices aren’t a luxury but a growth strategy.

    Doing it Right from the start: In practice

    Now that we understand why scalable and maintainable tech decisions are crucial early on, here are some practical strategies to help your startup avoid quick fixes and build a strong foundation.

    1. Prioritise Root Cause

    Don’t just patch, find and fix the real problem. For example, optimise slow database queries instead of repeatedly fixing slow responses.

    2. Adopt Agile

    Work in short cycles and use user feedback. Many fintech startups rely on agile to adapt quickly.

    3. Write Clean, Modular Code

    Keep code simple and flexible. Use modular design to evolve without costly rewrites.

    4. Test Early

    Use automated tests early to catch bugs. Improve stability by prioritising testing from the start.

    5. Review Regularly

    Hold frequent code and architecture reviews. Startups BoardClic and Metaito used expert code and architecture reviews to ensure scalable, robust platforms.

    6. Choose the Right Tech

    Pick tools that fit your goals and skills. Many startups use scalable, developer-friendly stacks like Elixir.

    7. Document Clearly

    Keep documentation up to date to help teams understand decisions and onboard new members fast.

    8. Don’t skip security checks

    It’s easier to fix security issues early than patch things up later. Audits, such as SAFE (Security Audit for Erlang and Elixir) , helped startups like Koll and Twine ensure the security of their systems early on, making it easier to scale with confidence and avoid nasty surprises.

    Starting with these habits cuts costly fixes later and sets your startup up for lasting growth.

    Balancing speed and quality without overengineering

    Startups must deliver quickly but avoid building overly complex solutions too soon. The key is focusing on essential features that address real user needs, while keeping the system flexible enough to adapt later. This helps avoid wasted effort on premature optimisation or unnecessary features.

    For more on this, check out our post: Common MVP mistakes: How to build smart without overbuilding .

    Build now, avoid startup tech mistakes later

    Startups move fast, but speed shouldn’t come at the cost of sustainability. Those early quick fixes and temporary solutions often end up sticking around. Over time, they slow you down, create technical debt, and make it harder to grow.

    You don’t need to build the perfect system from day one. But you do need a foundation that won’t hold you back.

    Make smart, thoughtful tech choices early. Keep things simple. Review regularly. Focus on value that lasts. That’s how you stay fast without sacrificing your future.
    If you’re ready to avoid common startup tech mistakes and build something that lasts, Erlang Solutions can help, so let’s talk .

    The post Avoiding Common Startup Tech Mistakes appeared first on Erlang Solutions .

    • Pl chevron_right

      Erlang Solutions: Avoiding Common Startup Tech Mistakes

      news.movim.eu / PlanetJabber • 5 June 2025 • 7 minutes

    When you’re moving quickly in a startup, taking shortcuts in your tech stack is tempting. A quick workaround here, a temporary fix there, with plans to tidy it all up later. But later can easily turn into never.

    Those early decisions, however small they seem, have a habit of sticking around. Over time, they slow you down, create technical debt, and make it harder to scale.

    This blog looks at how to avoid common startup tech mistakes by making smarter choices early on. You don’t need to build the perfect system from day one, but you do need to build something you won’t regret.

    The risks of rushing your tech stack decisions

    Your tech stack is the foundation of your product. Making quick choices to just keep things often comes with hidden costs.

    Common examples of early tech shortcuts

    • Choosing tools based on ease rather than long-term fit
    • Using third-party services without proper integration planning
    • Avoiding proper system design to save time
    • Stacking too many frameworks or libraries to plug gaps quickly
    • Skipping documentation, testing, or version control in the name of speed

    What could go wrong?

    Here are some of the common risks that come with rushing tech stack choices:

    Risk Impact
    Technical debt Every short-term choice adds friction later. Over time, progress slows as the team spends more time managing issues than delivering value.
    Security gaps Fast fixes can lead to poorly secured systems, especially when sensitive data is involved or best practices are skipped.
    Fragile foundations A patchwork stack becomes hard to maintain, debug, or scale, and onboarding new developers becomes a headache.
    Scaling problems Systems built for “now” can’t always support growth. Quick fixes often ignore load handling, resulting in slowdowns or breakdowns at scale.
    Innovation slowdown When all your energy goes into fixing past decisions, there’s little room left for building what’s next.

    The business cost of technical shortcuts

    They directly impact a startup’s ability to grow. From wasted dev time to lost customer trust, the cost of early shortcuts adds up fast. That’s not the kind of overhead most startups can afford.

    The long-term cost of technical debt

    We touched on technical debt earlier as one of the key risks of rushing early tech decisions. Now let’s look at it more closely, because for many startups, it’s the most persistent and costly issue that comes from cutting corners.

    Technical debt is the build-up of compromises made during development, from skipping tests and rushing features to patching bugs without addressing their root cause. These short-term choices eventually slow everything down, making it harder and more expensive to move forward.

    Let’s break down the long-term impact:

    The hidden costs of technical debt

    Consequence What it means
    Slower development Developers spend more time fixing old issues than building new features, reducing overall velocity.
    More bugs, more fire-fighting Poorly maintained code leads to more frequent and severe bugs, increasing customer support and downtime.
    Low team morale Constantly dealing with messy code creates frustration and burnout, which can hurt retention.
    Harder to scale As the product grows, tech debt makes it harder to add new features or pivot without causing breakages.
    Security risks Outdated code or rushed fixes often introduce vulnerabilities that can be exploited later.
    Increased costs Fixing problems later is far more expensive, both in time and budget.

    A Stripe report found developers spend up to 42% of their week handling technical debt. CIO research suggests 20–40% of IT budgets are spent addressing it.

    When it gets out of control

    Technical debt can halt progress entirely. We’ve seen startups and scale-ups locked into outdated or fragmented systems, where maintaining or updating anything becomes nearly impossible.

    Here are a few real-world scenarios:

    • Legacy overload : Systems running well past their intended lifespan, no longer supported or secure.
    • Integration failure : Poorly connected tools and services that don’t talk to each other, slowing everything down.
    • Scaling bottlenecks : Infrastructure so rigid that every new feature or user pushes it closer to breaking point.

    Security crises : Outdated code with known vulnerabilities, eventually forcing a full rebuild after a breach.

    What startups can do about it:

    You can’t avoid technical debt entirely, but you can manage it by:

    • Prioritising clean, maintainable code from day one
    • Setting time aside for refactoring and testing
    • Regularly reviewing architecture decisions
    • Choosing tools that support long-term scalability, not just quick wins

    Startups that manage technical debt proactively stay more adaptable, secure, and focused on building the future.

    Why scalability matters from day one

    Tech built in a rush might work for an MVP (minimum viable product), but without scalability and maintainability in mind, it becomes a liability, something we cover in more detail in our post on common MVP mistakes.

    60% of startups face major scalability issues within their first three years (McKinsey) . These problems aren’t just technical; they slow growth, frustrate users, and drain time and resources.

    Here’s why it’s critical to get it right from the start:

    1. Scaling later is harder and more expensive

    Retrofitting scalability into an existing product or tech is rarely clean. The cost (in both time and money) often outweighs what it would’ve taken to plan it earlier.

    2. Maintainable code accelerates growth

    Clean, modular code helps teams ship faster, fix bugs quicker, and onboard new engineers smoothly. Poor code slows everything down.

    3. Users don’t tolerate failure

    Unscalable systems break under pressure, which is exactly when users start showing up. That erodes trust, kills momentum, and makes customer retention harder.

    4. Bad tech choices can limit your future

    Tech that isn’t built to adapt can lock you into tools, vendors, or architectures that no longer serve your goals. That makes pivots and product evolution harder.

    Early-stage teams often defer these decisions to “later.” But in startups, later usually means too late . Thoughtful, scalable, and maintainable tech choices aren’t a luxury but a growth strategy.

    Doing it Right from the start: In practice

    Now that we understand why scalable and maintainable tech decisions are crucial early on, here are some practical strategies to help your startup avoid quick fixes and build a strong foundation.

    1. Prioritise Root Cause

    Don’t just patch, find and fix the real problem. For example, optimise slow database queries instead of repeatedly fixing slow responses.

    2. Adopt Agile

    Work in short cycles and use user feedback. Many fintech startups rely on agile to adapt quickly.

    3. Write Clean, Modular Code

    Keep code simple and flexible. Use modular design to evolve without costly rewrites.

    4. Test Early

    Use automated tests early to catch bugs. Improve stability by prioritising testing from the start.

    5. Review Regularly

    Hold frequent code and architecture reviews. Startups BoardClic and Metaito used expert code and architecture reviews to ensure scalable, robust platforms.

    6. Choose the Right Tech

    Pick tools that fit your goals and skills. Many startups use scalable, developer-friendly stacks like Elixir.

    7. Document Clearly

    Keep documentation up to date to help teams understand decisions and onboard new members fast.

    8. Don’t skip security checks

    It’s easier to fix security issues early than patch things up later. Audits, such as SAFE (Security Audit for Erlang and Elixir) , helped startups like Koll and Twine ensure the security of their systems early on, making it easier to scale with confidence and avoid nasty surprises.

    Starting with these habits cuts costly fixes later and sets your startup up for lasting growth.

    Balancing speed and quality without overengineering

    Startups must deliver quickly but avoid building overly complex solutions too soon. The key is focusing on essential features that address real user needs, while keeping the system flexible enough to adapt later. This helps avoid wasted effort on premature optimisation or unnecessary features.

    For more on this, check out our post: Common MVP mistakes: How to build smart without overbuilding .

    Build now, avoid startup tech mistakes later

    Startups move fast, but speed shouldn’t come at the cost of sustainability. Those early quick fixes and temporary solutions often end up sticking around. Over time, they slow you down, create technical debt, and make it harder to grow.

    You don’t need to build the perfect system from day one. But you do need a foundation that won’t hold you back.

    Make smart, thoughtful tech choices early. Keep things simple. Review regularly. Focus on value that lasts. That’s how you stay fast without sacrificing your future.
    If you’re ready to avoid common startup tech mistakes and build something that lasts, Erlang Solutions can help, so let’s talk .

    The post Avoiding Common Startup Tech Mistakes appeared first on Erlang Solutions .

    • Pl chevron_right

      Erlang Solutions: Avoiding Common Startup Tech Mistakes

      news.movim.eu / PlanetJabber • 5 June 2025 • 7 minutes

    When you’re moving quickly in a startup, taking shortcuts in your tech stack is tempting. A quick workaround here, a temporary fix there, with plans to tidy it all up later. But later can easily turn into never.

    Those early decisions, however small they seem, have a habit of sticking around. Over time, they slow you down, create technical debt, and make it harder to scale.

    This blog looks at how to avoid common startup tech mistakes by making smarter choices early on. You don’t need to build the perfect system from day one, but you do need to build something you won’t regret.

    The risks of rushing your tech stack decisions

    Your tech stack is the foundation of your product. Making quick choices to just keep things often comes with hidden costs.

    Common examples of early tech shortcuts

    • Choosing tools based on ease rather than long-term fit
    • Using third-party services without proper integration planning
    • Avoiding proper system design to save time
    • Stacking too many frameworks or libraries to plug gaps quickly
    • Skipping documentation, testing, or version control in the name of speed

    What could go wrong?

    Here are some of the common risks that come with rushing tech stack choices:

    Risk Impact
    Technical debt Every short-term choice adds friction later. Over time, progress slows as the team spends more time managing issues than delivering value.
    Security gaps Fast fixes can lead to poorly secured systems, especially when sensitive data is involved or best practices are skipped.
    Fragile foundations A patchwork stack becomes hard to maintain, debug, or scale, and onboarding new developers becomes a headache.
    Scaling problems Systems built for “now” can’t always support growth. Quick fixes often ignore load handling, resulting in slowdowns or breakdowns at scale.
    Innovation slowdown When all your energy goes into fixing past decisions, there’s little room left for building what’s next.

    The business cost of technical shortcuts

    They directly impact a startup’s ability to grow. From wasted dev time to lost customer trust, the cost of early shortcuts adds up fast. That’s not the kind of overhead most startups can afford.

    The long-term cost of technical debt

    We touched on technical debt earlier as one of the key risks of rushing early tech decisions. Now let’s look at it more closely, because for many startups, it’s the most persistent and costly issue that comes from cutting corners.

    Technical debt is the build-up of compromises made during development, from skipping tests and rushing features to patching bugs without addressing their root cause. These short-term choices eventually slow everything down, making it harder and more expensive to move forward.

    Let’s break down the long-term impact:

    The hidden costs of technical debt

    Consequence What it means
    Slower development Developers spend more time fixing old issues than building new features, reducing overall velocity.
    More bugs, more fire-fighting Poorly maintained code leads to more frequent and severe bugs, increasing customer support and downtime.
    Low team morale Constantly dealing with messy code creates frustration and burnout, which can hurt retention.
    Harder to scale As the product grows, tech debt makes it harder to add new features or pivot without causing breakages.
    Security risks Outdated code or rushed fixes often introduce vulnerabilities that can be exploited later.
    Increased costs Fixing problems later is far more expensive, both in time and budget.

    A Stripe report found developers spend up to 42% of their week handling technical debt. CIO research suggests 20–40% of IT budgets are spent addressing it.

    When it gets out of control

    Technical debt can halt progress entirely. We’ve seen startups and scale-ups locked into outdated or fragmented systems, where maintaining or updating anything becomes nearly impossible.

    Here are a few real-world scenarios:

    • Legacy overload : Systems running well past their intended lifespan, no longer supported or secure.
    • Integration failure : Poorly connected tools and services that don’t talk to each other, slowing everything down.
    • Scaling bottlenecks : Infrastructure so rigid that every new feature or user pushes it closer to breaking point.

    Security crises : Outdated code with known vulnerabilities, eventually forcing a full rebuild after a breach.

    What startups can do about it:

    You can’t avoid technical debt entirely, but you can manage it by:

    • Prioritising clean, maintainable code from day one
    • Setting time aside for refactoring and testing
    • Regularly reviewing architecture decisions
    • Choosing tools that support long-term scalability, not just quick wins

    Startups that manage technical debt proactively stay more adaptable, secure, and focused on building the future.

    Why scalability matters from day one

    Tech built in a rush might work for an MVP (minimum viable product), but without scalability and maintainability in mind, it becomes a liability, something we cover in more detail in our post on common MVP mistakes.

    60% of startups face major scalability issues within their first three years (McKinsey) . These problems aren’t just technical; they slow growth, frustrate users, and drain time and resources.

    Here’s why it’s critical to get it right from the start:

    1. Scaling later is harder and more expensive

    Retrofitting scalability into an existing product or tech is rarely clean. The cost (in both time and money) often outweighs what it would’ve taken to plan it earlier.

    2. Maintainable code accelerates growth

    Clean, modular code helps teams ship faster, fix bugs quicker, and onboard new engineers smoothly. Poor code slows everything down.

    3. Users don’t tolerate failure

    Unscalable systems break under pressure, which is exactly when users start showing up. That erodes trust, kills momentum, and makes customer retention harder.

    4. Bad tech choices can limit your future

    Tech that isn’t built to adapt can lock you into tools, vendors, or architectures that no longer serve your goals. That makes pivots and product evolution harder.

    Early-stage teams often defer these decisions to “later.” But in startups, later usually means too late . Thoughtful, scalable, and maintainable tech choices aren’t a luxury but a growth strategy.

    Doing it Right from the start: In practice

    Now that we understand why scalable and maintainable tech decisions are crucial early on, here are some practical strategies to help your startup avoid quick fixes and build a strong foundation.

    1. Prioritise Root Cause

    Don’t just patch, find and fix the real problem. For example, optimise slow database queries instead of repeatedly fixing slow responses.

    2. Adopt Agile

    Work in short cycles and use user feedback. Many fintech startups rely on agile to adapt quickly.

    3. Write Clean, Modular Code

    Keep code simple and flexible. Use modular design to evolve without costly rewrites.

    4. Test Early

    Use automated tests early to catch bugs. Improve stability by prioritising testing from the start.

    5. Review Regularly

    Hold frequent code and architecture reviews. Startups BoardClic and Metaito used expert code and architecture reviews to ensure scalable, robust platforms.

    6. Choose the Right Tech

    Pick tools that fit your goals and skills. Many startups use scalable, developer-friendly stacks like Elixir.

    7. Document Clearly

    Keep documentation up to date to help teams understand decisions and onboard new members fast.

    8. Don’t skip security checks

    It’s easier to fix security issues early than patch things up later. Audits, such as SAFE (Security Audit for Erlang and Elixir) , helped startups like Koll and Twine ensure the security of their systems early on, making it easier to scale with confidence and avoid nasty surprises.

    Starting with these habits cuts costly fixes later and sets your startup up for lasting growth.

    Balancing speed and quality without overengineering

    Startups must deliver quickly but avoid building overly complex solutions too soon. The key is focusing on essential features that address real user needs, while keeping the system flexible enough to adapt later. This helps avoid wasted effort on premature optimisation or unnecessary features.

    For more on this, check out our post: Common MVP mistakes: How to build smart without overbuilding .

    Build now, avoid startup tech mistakes later

    Startups move fast, but speed shouldn’t come at the cost of sustainability. Those early quick fixes and temporary solutions often end up sticking around. Over time, they slow you down, create technical debt, and make it harder to grow.

    You don’t need to build the perfect system from day one. But you do need a foundation that won’t hold you back.

    Make smart, thoughtful tech choices early. Keep things simple. Review regularly. Focus on value that lasts. That’s how you stay fast without sacrificing your future.
    If you’re ready to avoid common startup tech mistakes and build something that lasts, Erlang Solutions can help, so let’s talk .

    The post Avoiding Common Startup Tech Mistakes appeared first on Erlang Solutions .

    • Pl chevron_right

      Debian XMPP Team: XMPP/Jabber Debian 13 Trixie News

      news.movim.eu / PlanetJabber • 29 May 2025 • 3 minutes

    Debian 13 "Trixie" full freeze has started 2025-05-17, so this is a good time to take a look at some of the features, that this release will bring. Here we will focus on packages related to XMPP, a.k.a. Jabber .

    XMPP is a universal communication protocol for instant messaging, push notifications, IoT, WebRTC, and social applications. It has existed since 1999, originally called "Jabber", it has a diverse and active developers community.

    Clients

    Servers

    Libraries

    Gateways/Transports

    • Biboumi , a gateway between XMPP and IRC, upgrades from 9.0 to 9.0+20241124.
    • Debian 13 Trixie includes Slidge 0.2.12 and Matridge 0.2.3 for the first time! It is a gateway between XMPP and Matrix, with support for many chat features.

    Not in Trixie

    • Spectrum 2 , a gateway from XMPP to various other messaging systems, did not make it into Debian 13, because it depends on Swift , which has release critical bugs and therefore cannot be part of a stable release.
    • Pl chevron_right

      Debian XMPP Team: XMPP/Jabber Debian 13 Trixie News

      news.movim.eu / PlanetJabber • 29 May 2025 • 3 minutes

    Debian 13 "Trixie" full freeze has started 2025-05-17, so this is a good time to take a look at some of the features, that this release will bring. Here we will focus on packages related to XMPP, a.k.a. Jabber .

    XMPP is a universal communication protocol for instant messaging, push notifications, IoT, WebRTC, and social applications. It has existed since 1999, originally called "Jabber", it has a diverse and active developers community.

    Clients

    Servers

    Libraries

    Gateways/Transports

    • Biboumi , a gateway between XMPP and IRC, upgrades from 9.0 to 9.0+20241124.
    • Debian 13 Trixie includes Slidge 0.2.12 and Matridge 0.2.3 for the first time! It is a gateway between XMPP and Matrix, with support for many chat features.

    Not in Trixie

    • Spectrum 2 , a gateway from XMPP to various other messaging systems, did not make it into Debian 13, because it depends on Swift , which has release critical bugs and therefore cannot be part of a stable release.
    • Pl chevron_right

      Debian XMPP Team: XMPP/Jabber Debian 13 Trixie News

      news.movim.eu / PlanetJabber • 29 May 2025 • 3 minutes

    Debian 13 "Trixie" full freeze has started 2025-05-17, so this is a good time to take a look at some of the features, that this release will bring. Here we will focus on packages related to XMPP, a.k.a. Jabber .

    XMPP is a universal communication protocol for instant messaging, push notifications, IoT, WebRTC, and social applications. It has existed since 1999, originally called "Jabber", it has a diverse and active developers community.

    Clients

    Servers

    Libraries

    Gateways/Transports

    • Biboumi , a gateway between XMPP and IRC, upgrades from 9.0 to 9.0+20241124.
    • Debian 13 Trixie includes Slidge 0.2.12 and Matridge 0.2.3 for the first time! It is a gateway between XMPP and Matrix, with support for many chat features.

    Not in Trixie

    • Spectrum 2 , a gateway from XMPP to various other messaging systems, did not make it into Debian 13, because it depends on Swift , which has release critical bugs and therefore cannot be part of a stable release.