Category: tech

  • Tailscale killed my DNS

    I am working on a remote location today, on a shared venue network.

    After rebooting my Mac I could no longer connect to any website domain, which led me to believe that DNs was not resolving. And indeed, pinging www.google.com gave no results. Even when tethered to my iPhone, I could not connect to any website. Connecting to VPN by IP did work though, and pinging 8.8.8.8 worked fine as well.

    Luckily, I could search for clues on my phone, and ran into this command that I have not used before:

    scutil --dns which gives you a nice list of DNS resolvers as they are used by the system, and, on top of that list this entry:

    resolver #1
      search domain[0] : tailf67a92.ts.net
      nameserver[0] : 100.100.100.100
      if_index : 24 (utun4)
      flags    : Supplemental, Request A records, Request AAAA records
      reach    : 0x00000003 (Reachable,Transient Connection)
      order    : 102000

    I restarted Tailscale, and we are online again 🎉.

  • Enable compatibility mode in WooCommerce

    If you have setup a WooCommerce shop recently, or have enabled their HPOS1 you will want to enable compatibility mode as soon as you use any extension.

    I’m running into issues with WooCommerce Memberships not able to create memberships for users, because it cannot find the users related to an order:

    /**
     * Returns users IDs from orders that contain products that could grant access to a given plan.
     *
     * TODO When WooCommerce starts using alternate data stores for products (perhaps from WC 3.5+) this method may require an update as it performs a direct SQL query assuming a standard WPDB data organization {FN 2018-07-23}
     *
     * @since 1.10.6
     *
     * @param int[] $access_product_ids array of product IDs that grant access to a plan upon purchase
     * @return int[] array of user IDs
     */
    private function get_users_for_retroactive_access( array $access_product_ids ) {
    	global $wpdb;
    
    	if ( ! empty( $access_product_ids ) ) {
    
    		// get orders that contain an access granting product (or variation) to the given plan
    		$product_ids  = Strings_Helper::esc_sql_in_ids( $access_product_ids );
    		$orders_table = Framework\SV_WC_Order_Compatibility::get_orders_table();
    		$order_id_col = Framework\SV_WC_Plugin_Compatibility::is_hpos_enabled() ? 'id' : 'ID';
    		$order_ids    = $wpdb->get_col(  "
    			SELECT DISTINCT orders.{$order_id_col}
    			FROM {$wpdb->prefix}woocommerce_order_itemmeta AS order_item_meta,
    			     {$wpdb->prefix}woocommerce_order_items AS order_items,
    			     $orders_table AS orders
    			WHERE order_items.order_item_id = order_item_meta.order_item_id
    			AND order_items.order_id = orders.{$order_id_col}
    			AND ( ( order_item_meta.meta_key LIKE '_product_id'   AND order_item_meta.meta_value IN ({$product_ids}) )
    			 OR   ( order_item_meta.meta_key LIKE '_variation_id' AND order_item_meta.meta_value IN ({$product_ids}) ) )
    		" );
    
    		if ( ! empty( $order_ids ) ) {
    
    			// get user IDs for the found orders
    			$order_ids = Strings_Helper::esc_sql_in_ids( $order_ids );
    			$user_ids  = $wpdb->get_col( "
    				SELECT posts_meta.meta_value
    				FROM {$wpdb->prefix}postmeta AS posts_meta
    				WHERE posts_meta.post_id IN ({$order_ids})
    				AND posts_meta.meta_key = '_customer_user'
    			" );
    		}
    	}
    
    	return ! empty( $user_ids ) ? array_unique( array_map( 'absint', array_values( $user_ids ) ) ) : [];
    }

    With HPOS, the customer id is saved in the wp_wc_orders table instead.

    1. High-performance order storage ↩︎
  • How to prepare for a DDoS

    How to prepare for a DDoS

    This post is about the product we are building at Toolsquare.io

    The recent/ongoing DDoS1 in the Netherlands impacted our customers, and our own product.

    Although we don’t have publicly accessible endpoints on the customers network, we dó have to use their network connection to connect our hardware with our cloud platform. As an IOT solution, this is obvious. We do not supply our own WiFi network or cellular network, in order to reduce costs.

    Offline Mode

    When creating an IoT productivity system, the last thing you want is to get in the way of your user’s productivity. That’s why we implemented an offline mode on our hardware that allows the user to continue to work in case there is no network connectivity. This feature can be enabled on a per-device basis.

    Slow is not Offline

    As a consequence of the ongoing DDoS attack, network traffic is slow. This leads to long connection times, and response (failure to connect or connection success) takes more time to come in. Some of our hardware units were failing to go into offline mode because of this, and stuck in a reboot loop. Once we figured this out, a fix was quickly deployed and our customers can continue their work in offline mode.

    You’ll never test enough

    We have a robust test plan with unit tests, integration tests and end to end tests that takes many things that can be simulated into account. After today’s experience we will add slow network testing for our hardware/firmware to this by building a Raspberry Pi network emulation device that can simulate slow network behaviour.

    1. Distributed Denial of Service attack ↩︎
  • WooCommerce Brands rollout

    With WooCommerce 9.4, WooCommerce Brands is getting rolled out to a cohort (5%) of installs.

    If you do not want to participate in this change set the option woocommerce_remote_variant_assignment to a higher value, e.g. 111

    <?php
    /**
     * Ensures that the Brands feature is released initially only to 5% of users.
     *
     * @return bool
     */
    public static function is_enabled() {
    	$assignment = get_option( 'woocommerce_remote_variant_assignment', false );
    
    	if ( false === $assignment ) {
    		return false;
    	}
    	return ( $assignment <= 6 ); // Considering 5% of the 0-120 range.
    }

    While this is a good feature, it can break your existing brands solution as it did in my case on an existing ecommerce setup.

  • Not now, Tim Apple

    "Your disk is almost full" alert
Save space by optimising storage.

    UPDATE:

    Screenshot: com.apple.wallpaper.caches 568,82 GB

    It is perfectly reasonable to keep half a Terabyte of wallpaper caches, MacOS.

    PS: shoutout to DaisyDisk app

  • Document Tabs in Google Docs

    Today, I ran into this new feature in Google Docs for the first time.

    It allows you to create tabs within your document, which become like separate pages or chapters. Every tab is isolated from each other, you cannot scroll from one tab to another. I expect this to lead to a lot of confusion for people unaware of this feature.

    Collapsed vs rexpanded tabs in Google docs

    Discoverability leaves a lot to be desired.

    I am a heavy user of document outlines, which are now integrated in this feature, so it looks like I will be using this anyway 😬.

  • Added a photos page

    I just added a photos page to this site. It’s rather short and needs some optimisation, but I’m working on fixing both of theses issues.

    It’s really impressive what you can do with WordPress’ site editor today. Although I start hitting the limits of it. I’ll dive into the theming code later this week.

  • Self-review your code

    Self-review your code

    Something really resonated with me in the latest episode of the Under the Radar podcast: the concept of switching context and reviewing your own code before committing.

    I’m really happy to hear @marcoarment and @_Davidsmith discuss how they review every commit to validate all code that goes into version control.

    I often have a hard time selling this habits to junior devs (and even senior devs!). As a consequence I’ve often been rewriting git repository histories to remove passwords, PII1, zip files of several hundreds of megabytes (“git is so slow”) and even malware.

    I like to rethink my code architecture while reviewing and often go back to refactor, to take more edge-cases into account or for simplicity.

    I love using Fork for this, a great git UI with a good diff viewer, all in one app.

    1. Personally Identifiable Information, you want to be careful with that ↩︎

    Picture: Rice harvest on Louisiana farm by Karl Wiggers

  • NetNewsWire was not updating my RSS feed

    NetNewsWire is having trouble refreshing my RSS feed, both on Mac desktop (6.1.8) and iOS (6.1.5 Build 6135).

    • I tested with an alternative RSS reader: Unread, which updates the feed fine.
    • I double checked my caching and expiration headers, which also appear ok.
    • I went through the log files and saw many entries for Unread and some for Google bot (hello 👋)
    • I removed the feed from NNW and re-added it, but no success…

    I’m tempted to try and build the desktop app from source, since the source is available on Github, but that will require some extra free time.

    UPDATE 2025.01.02: I installed the TestFlight build (6.1.6 6141) and the issue persists.

    UPDATE 2025.01.03: TestFlight build 6.1.6 6142 installed overnight and the issue is fixed 🎉! Now waiting for the next desktop release.