<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:content="http://purl.org/rss/1.0/modules/content/">
  <channel>
    <title>Paul Smith's Blog - Technology</title>

    <link>https://www.dasmirnov.net/categories/technology/</link>
    <description>Recent content on Paul Smith's Blog, covering technology, politics and gaming.</description>
    <image>
      <url>https://www.dasmirnov.net/blog/media/blogs/paulsmith/img_4525_2_.jpg</url>
      <link>https://www.dasmirnov.net/blog/media/blogs/paulsmith/img_4525_2_.jpg</link>
    </image>
    <generator>Hugo -- gohugo.io</generator>
    <language>en</language>
    <lastBuildDate>Wed, 31 Dec 2025 14:02:00 +0000</lastBuildDate><atom:link href="https://www.dasmirnov.net/categories/technology/index.xml" rel="self" type="application/rss+xml" />
    <item>
      <title>Mastodon, culture and censorship</title>
      <link>https://www.dasmirnov.net/blog/mastodon-culture-censorship/</link>
      <pubDate>Wed, 31 Dec 2025 14:02:00 +0000</pubDate>
      
      <guid>https://www.dasmirnov.net/blog/mastodon-culture-censorship/</guid>
      <description>Mastodon, a culture of censorship not fit for a new open internet.</description>
      <content:encoded><![CDATA[<p>As you may be aware I&rsquo;ve been Mastodon for a while - I actually run two small instances, one will be closing shortly, hence this post.  The Fediverse has much promise and still does, despite an ever-increasing tendency to larger and larger instances, made all the worse by the Mastodon app strongly encouraging you to sign up on the largest instance mastodon dot social.</p>
<p>Back over two years ago I made a post, looking at some non-mainstream political accounts on the largest instance mastodon dot social, 75% were hidden or blocked.  These were all identifiably left-wing with an anti-war, anti-NATO stance - I didn&rsquo;t bother checking right-wing accounts as I think universally everyone will acknowledge they won&rsquo;t last 10 minutes on Mastodon.</p>
<p><img loading="lazy" src="mastodoncensorship.png" alt="Four accounts checked at random on mastodon dot social, 75% banned or hidden"  />
</p>
<p>Anyway this is the main reason I&rsquo;m binning one of my instances off - the culture of Mastodon is just not suitable for any sort of political discussion outside of a very narrow bourgeois-liberal spectrum, X is actually much better for this nowadays.</p>
<p>This is without addressing all the other issues:</p>
<ul>
<li>Fediblock wars where whole instances just get blocked by other instances.  Their users left wondering why they can&rsquo;t communicate with people they were talking to yesterday.</li>
<li>Or Mastodon dot lol shutting down, with over seventy three thousand users, because a bunch of trans-activists were harassing people who wanted to play the computer game Hogwarts Legacy.</li>
</ul>
<p>The list is almost endless.</p>
<p>Anyway I&rsquo;ve used various <a href="https://nostr.com/">Nostr</a> applications for a while, I used to run a relay for it a couple of years ago.  I think as it and the applications for it matures it offers a lot of potential.  And technically, unlike ActivityPub where your identify is tied to a server and can get nuked or blocked for a variety of reasons.</p>
<p>Or we just go back in time to twenty years ago and go on the blogosphere 🙌.</p>
<h3 id="more-reading">More reading</h3>
<ul>
<li><a href="https://medium.com/@bblfish/on-mastodon-censorship-e8429f52e2fc">On Mastodon censorship</a></li>
<li><a href="https://blog.mbirth.uk/2025/05/30/mastodon-social-and-shadowbanning.html">Mastodon.social shadowbanned me</a></li>
</ul>
]]></content:encoded>
    </item>
    
    <item>
      <title>Glances Web UI broken on Debian, Ubuntu, Mint etc</title>
      <link>https://www.dasmirnov.net/blog/glances-web-ui-broken-in-debian-ubuntu-mint-etc/</link>
      <pubDate>Sat, 13 May 2023 15:19:00 +0000</pubDate>
      
      <guid>https://www.dasmirnov.net/blog/glances-web-ui-broken-in-debian-ubuntu-mint-etc/</guid>
      <description>Issues with Glances Web UI and the workaround for those on effecting distros</description>
      <content:encoded><![CDATA[<p>When upgrading some of my servers to Ubuntu 22.04 earlier this year I noticed the Web UI for Glances was broken, didn&rsquo;t do much investigation at the time, assumed it was a dodgy update or known compatibility issue that would be sorted in time. But noticed the same issue on Linux Mint 22.1 today, almost four months later.</p>
<p>According to <a href="https://github.com/nicolargo/glances/issues/2021#issuecomment-1107863566">epsilon77</a> this is because:</p>
<blockquote>
<p>Hello! I am maintainer of glances in Debian, for Debian policy, the packages should not include prebult files, for this reason, we had to remove those js files from debian package. and this change does WEB-UI useless.</p>
</blockquote>
<p>There&rsquo;s a few suggestions in that thread however I&rsquo;d suggest just running:</p>
<pre><code>wget https://github.com/nicolargo/glances/archive/refs/tags/v3.2.7.tar.gz
tar -xzf v3.2.7.tar.gz
sudo cp -r glances-3.2.7/glances/outputs/static/public/ /usr/lib/python3/dist-packages/glances/outputs/static/
rm v3.2.7.tar.gz
rm -r glances-3.2.7
</code></pre>
<p>That&rsquo;ll download the files we need, extract them, copy them into the Glances install directory and then remove the downloaded bits once we&rsquo;re done. Refreshing the browser should show the Glances Web UI instead of a blank white page.</p>
]]></content:encoded>
    </item>
    
    <item>
      <title>Installing Pixelfed with Docker Compose</title>
      <link>https://www.dasmirnov.net/blog/installing-pixelfed-with-docker-compose/</link>
      <pubDate>Sun, 23 Apr 2023 15:44:00 +0000</pubDate>
      
      <guid>https://www.dasmirnov.net/blog/installing-pixelfed-with-docker-compose/</guid>
      <description>Quick notes on installing Pixelfed using Docker Compose</description>
      <content:encoded><![CDATA[<p>Just my quick notes on installing Pixelfed using Docker Compose, long term I&rsquo;d like to write this up into a proper guide.  Important things to note - Pixelfed as of the moment doesn&rsquo;t have an official Docker image, normally you&rsquo;d pull it from Github and build it yourself. However since version 0.11.5 I&rsquo;ve started using an existing image maintained by <a href="https://hub.docker.com/r/murazaki/pixelfed">Murazaki</a>.</p>
<h3 id="web-proxy">Web proxy</h3>
<ol>
<li>
<p>Assuming you&rsquo;re running Nginx on the web host you&rsquo;ll need to setup a proxy by adding something like this to your <code>.conf</code> file:</p>
<pre><code> location / {
   proxy_set_header Host $host;
   proxy_set_header X-Real-IP $remote_addr;
   proxy_set_header X-Forwarded-For $remote_addr;
   proxy_pass http://127.0.0.1:8080;
 }
</code></pre>
</li>
<li>
<p>If you&rsquo;re using Certbot, you may need to tweak how Nginx handles the ACME Challenge, I use the below to make sure the certificate request isn&rsquo;t proxied to Pixelfed:</p>
<pre><code> location /.well-known/acme-challenge/ {
   alias   /path/to/web/site/.well-known/acme-challenge/;
   allow all;
 }
</code></pre>
</li>
</ol>
<p>Please be aware Pixelfed expects to receive traffic from /.well-known/webfinger* and potentially other addresses for ActivityPub.</p>
<h3 id="pixelfed">Pixelfed</h3>
<ol>
<li>
<p>Grab the <code>docker-compose.yml</code> file off the <a href="https://github.com/pixelfed/pixelfed">Github repository</a>, we wanna comment out the build instructions and just use the above image, like the below for both the app and worker.</p>
<pre><code> # Comment to use dockerhub image
 #   build:
 #    context: .
 #      dockerfile: contrib/docker/Dockerfile.apache
 image: murazaki/pixelfed:edge-apache
</code></pre>
</li>
<li>
<p>Grab the <code>.env.docker</code> file off the repository, make sure to edit the below plus any database names and passwords etc:</p>
<pre><code> ## General Settings
 APP_NAME=&quot;Pixelfed Prod&quot;
 APP_ENV=production
 APP_DEBUG=false
 APP_URL=https://real.domain
 APP_DOMAIN=&quot;real.domain&quot;
 ADMIN_DOMAIN=&quot;real.domain&quot;
 SESSION_DOMAIN=&quot;real.domain&quot;
</code></pre>
</li>
</ol>
<p>Check through the file and change any other settings as required. Its quicker to do it before hand as by default Pixelfed will cache the config, requiring it to be cleared etc. Pixelfed does not handle changing domain after installing, so make sure you&rsquo;re happy with the domain you&rsquo;re using.</p>
<ol start="3">
<li>
<p>Ok we should be good to run <code>docker-compose up -d</code>.</p>
</li>
<li>
<p>Check any firewall rules that might be blocking the Docker bridge.</p>
</li>
<li>
<p>Generate a crypto key using <code>docker-compose exec app php artisan key:generate</code> this will also enter it into <code>.env.docker</code> for you, but you could run <code>cat .env.docker | grep APP_KEY</code> to check.</p>
</li>
<li>
<p>Restart the app <code>docker-compose restart app</code>.</p>
</li>
<li>
<p>Clear the config cache with <code>docker-compose exec app php artisan config:cache</code>.</p>
</li>
<li>
<p>Setup the database using <code>docker-compose exec app php artisan migrate</code>.</p>
</li>
<li>
<p>Restart the app <code>docker-compose restart app</code>.</p>
</li>
<li>
<p>Create your first user with <code>docker-compose exec app php artisan user:create</code>.</p>
</li>
<li>
<p>Visit the domain, you should be able to login.</p>
</li>
<li>
<p>Additional steps depending on how you want to run it, run <code>docker-compose exec app php artisan instance:actor</code> if you want to use ActivityPub.</p>
</li>
</ol>
<p>Should be good to go, generally after updates will need to run <code>docker-compose exec app php artisan migrate</code> and I&rsquo;ve had a few cases where profile pictures etc weren&rsquo;t loading after an update, fixed by running <code>docker-compose exec app php artisan storage:link</code>.</p>
<p><a href="https://docs.pixelfed.org/technical-documentation/artisan/">Detailed CLI documentation</a>. My <a href="https://pxlfd.dsnv.net/paul">Pixelfed account</a>.</p>
<p>Any questions? Feel free to drop a comment below.</p>
<h3 id="update-14th-june-2023">Update 14th June 2023</h3>
<p>I&rsquo;ve actually recently started using <a href="https://quay.io/repository/zknt/pixelfed">zknt&rsquo;s Docker image</a> this has got a few benefits, such as a startup script that automatically handles the initial install and does a migrate after an update. Additionally it is updated much more frequently.</p>
]]></content:encoded>
    </item>
    
    <item>
      <title>Cryptocurrency wallet coming to Edge</title>
      <link>https://www.dasmirnov.net/blog/cryptocurrency-wallet-coming-to-edge/</link>
      <pubDate>Sat, 18 Mar 2023 09:45:00 +0000</pubDate>
      
      <guid>https://www.dasmirnov.net/blog/cryptocurrency-wallet-coming-to-edge/</guid>
      <description>First screenshots of the new cryptocurrency wallet now in testing at Microsoft</description>
      <content:encoded><![CDATA[<p>I must admit, I&rsquo;m starting to get a little buried under the number of features being added to Microsoft Edge. To the point where I feel they need to add a minimum-install option to counter some of the bloat.</p>
<p>However, the cryptocurrency wallet is probably one of the better features, certainly better than searching the web for shopping vouchers. Hopefully come the next crypto cycle it&rsquo;ll be ready and help drive cryptocurrency into the mainstream by bringing &ldquo;web3&rdquo; direct to the browser.</p>
<p>Only real questions are how susceptible is this going to be to dodgy websites impersonating another? Will that alone cause more bad headlines featuring users that don&rsquo;t really know what they&rsquo;re doing getting scammed.  Obviously happens with bank cards, but that isn&rsquo;t newsworthy - and at least banks can stop or refund fraudulent transactions!</p>
<p><img loading="lazy" src="crypto2.png" alt="Crypto wallet welcome screen for internal testers"  />
</p>
<p><img loading="lazy" src="crypto3.png" alt="Crypto wallet screen showing available balances, definitely supports Ethereum mainnet"  />
</p>
<p><img loading="lazy" src="crypto4.png" alt="Crypto wallet transaction UI"  />
</p>
<p>Any chance we could get a decent RSS reader back in the browser please?</p>
]]></content:encoded>
    </item>
    
    <item>
      <title>Disable the Bing Discover button in Edge</title>
      <link>https://www.dasmirnov.net/blog/disable-the-bing-discover-button-in-edge/</link>
      <pubDate>Sun, 19 Feb 2023 09:42:00 +0000</pubDate>
      
      <guid>https://www.dasmirnov.net/blog/disable-the-bing-discover-button-in-edge/</guid>
      <description>How do you disable the Discover or Bing Discover button in Microsoft Edge which appeared in version v111</description>
      <content:encoded><![CDATA[<p>One of the new features in the development build of Edge at the moment is this Discover button, for some users its a purple star, for others its got the Bing logo, and as expected connects to a wide range of Bing services, including the new Chat AI. As it stands at the moment this will likely ship in version 111, i.e. the next big release.</p>
<p>I imagine the behaviour of this button will annoy many users as it looks distracting and opens on a long hover aswell as left-click, no doubt prompting many accidental openings.</p>
<p>I&rsquo;m leaving it on at the moment as I am trying to use Bing Chat in more of my workflows. However there&rsquo;s no hiding the fact a lot of people will regard this as bloatware and those people who want a minimum clean browser will want the option to disable it.</p>
<p>At the moment there are two ways, the first launching the browser with <code>--disable-features=msUndersideButton</code>. Below showing that setup in an Edge shortcut.</p>
<p><img loading="lazy" src="edge3.png" alt="Shortcut properties showing Edge launching with &amp;ndash;disable-features=msUndersideButton"  />
</p>
<p>Once launched with this, it&rsquo;ll disappear:</p>
<p><img loading="lazy" src="edge2.png" alt="Bing Discover button has now been removed from Edge UI"  />
</p>
<p>Alternatively you can add the below registry key and reload the policies in Edge to hide it:</p>
<p><code>[HKEY_LOCAL_MACHINE\SOFTWARE\Policies\Microsoft\Edge] &quot;HubsSidebarEnabled&quot;=dword:00000000</code></p>
<p>Hopefully in the future Microsoft will add a simple hide in a right-click menu on it, or at least an option exposed in the settings UI - or failing that a browser flag to hide it.</p>
<h3 id="update-18th-march-2023">Update, 18th March 2023</h3>
<p>The new Canary build 113 of Edge is now shipping with an option for this under Settings &gt; Sidebar &gt; Discover.</p>
<h3 id="update-23rd-april-2023">Update 23rd April 2023</h3>
<p>The toggle button in settings has now shipped in version 112.</p>
<p><img loading="lazy" src="bingdiscover.png" alt="Turn off Bing Discover button in Settings"  />
</p>
]]></content:encoded>
    </item>
    
    <item>
      <title>The New Bing AI Assistant</title>
      <link>https://www.dasmirnov.net/blog/the-new-bing-ai-assistant/</link>
      <pubDate>Sat, 18 Feb 2023 10:31:00 +0000</pubDate>
      
      <guid>https://www.dasmirnov.net/blog/the-new-bing-ai-assistant/</guid>
      <description>A blog post about the new Bing Chat AI assistant, written by itself, using a number of sources for its information.</description>
      <content:encoded><![CDATA[<p>Please note: This entire article was written by Bing Chat AI assistant after asking it to write a blog post about itself and talk about some of its features. None of the grammer or spelling has been changed, all I did was add &ldquo;Please leave a comment below.&rdquo; to the very end of the article.</p>
<p>Microsoft has recently launched a new version of its Bing search engine that features an AI-powered assistant called Chat. Chat is based on OpenAI&rsquo;s ChatGPT technology, which is a chatbot that can generate natural and engaging responses to user queries. In this blog post, we will explore what Chat can do, how it works, and what are some of its benefits and challenges.</p>
<h3 id="what-can-chat-do">What can Chat do?</h3>
<p>Chat can answer questions, provide information, and offer suggestions based on web searches. It can also engage in more informal and personal conversations with users, such as telling jokes, stories, or opinions. Chat can understand natural language and context, so users can ask questions however they like, do complex searches, follow up, and make refinements in chat.</p>
<p>For example, if you ask Chat &ldquo;What is the best laptop for gaming?&rdquo;, it will show you some relevant web results and also ask you some follow-up questions to narrow down your search criteria. You can then chat with Chat to compare different models, features, prices, reviews, etc.</p>
<p>Chat can also generate creative content such as poems, lyrics, code snippets etc., using its own words and knowledge. For example if you ask Chat &ldquo;Write me a poem about love&rdquo;, it will generate something like this:</p>
<blockquote>
<p>Love is more than just a word<br>
It&rsquo;s a feeling that fills your heart<br>
It&rsquo;s a bond that never breaks apart<br>
It&rsquo;s a light that guides your way<br>
It&rsquo;s a smile that brightens your day<br>
Love is more than just a word<br>
It&rsquo;s a gift that you give and receive</p>
</blockquote>
<h3 id="how-does-chat-work">How does Chat work?</h3>
<p>Chat is built on top of OpenAI&rsquo;s GPT-3 family of large language models. GPT-3 is an AI system that can generate text on any topic given some input text. It has been trained on billions of words from the internet and books.</p>
<p>However GPT-3 alone cannot handle dialogue very well as it lacks consistency, personality, and safety. That&rsquo;s why OpenAI developed ChatGPT which is a chatbot that has been fine-tuned using both supervised and reinforcement learning techniques.</p>
<p>Supervised learning means that human experts have labeled some data (such as conversations) with correct responses for the chatbot to learn from. Reinforcement learning means that human feedback (such as ratings or comments) has been used to reward or punish the chatbot for its outputs.</p>
<p>By combining these two methods OpenAI was able to create ChatGPT which can generate more coherent, relevant, and appropriate responses than GPT-3 alone.</p>
<p>Microsoft has integrated ChatGPT into Bing using its own proprietary technology called Project Conversation Engine (PCE). PCE allows Bing to leverage multiple sources of information such as web results, images, videos, maps etc., to provide rich answers to user queries.</p>
<p>PCE also enables Bing to handle multiple domains such as news, shopping, travel etc., and switch between them seamlessly depending on user intent.</p>
<h3 id="what-are-the-benefits-of-chat">What are the benefits of Chat?</h3>
<p>Chat offers several benefits for users who want to get more out of their web searches. Some of these benefits are:</p>
<ul>
<li>Faster and easier access to information: Users don&rsquo;t have to type long queries or browse through multiple pages to find what they are looking for. They can simply ask Chat in natural language and get quick answers.</li>
<li>More comprehensive and personalized results: Users can get more details about their topics of interest by chatting with Chat. They can also get tailored suggestions based on their preferences and needs.</li>
<li>More fun and engaging experience: Users can enjoy chatting with Chat as it has a friendly personality and sense of humor. They can also explore their curiosity by asking Chat anything they want.</li>
<li>More creative possibilities: Users can use Chat as a source of inspiration by asking it to generate content such as poems, lyrics, code snippets etc., for them.</li>
</ul>
<h3 id="what-are-some-challenges-or-limitations-of-using-bing-and-chatgpt">What are some challenges or limitations of using Bing and ChatGPT?</h3>
<p>Bing with ChatGPT is still an experimental technology that is undergoing testing and improvement. As such, it may encounter some challenges or limitations such as:</p>
<ul>
<li>It may not always provide accurate or relevant answers to your questions.</li>
<li>It may sometimes generate inappropriate or offensive texts that do not reflect Microsoft&rsquo;s values or policies.</li>
<li>It may get confused or behave oddly if you engage in very long chat sessions with it  .</li>
</ul>
<p>Microsoft advises users to exercise caution when using Bing with ChatGPT and report any issues or feedback they encounter.</p>
<h3 id="conclusion">Conclusion</h3>
<p>Bing with ChatGPT is an innovative feature that aims to enhance users&rsquo; search experience by providing them with intelligent, conversational, and personalized answers. It offers users several benefits such as saving time, getting diverse perspectives, learning new things, and having fun. However, it also has some challenges or limitations such as accuracy issues, inappropriate texts, and confusion problems.</p>
<p>If you want to try out this feature yourself, you need to use Microsoft Edge browser and go to <a href="https://www.bing.com/new">www.bing.com/new</a> or download the new Edge browser from here: <a href="https://www.microsoft.com/en-us/edge">https://www.microsoft.com/en-us/edge</a></p>
<p>What do you think about this feature? Do you find it useful or interesting? Do you have any questions or feedback? Please leave a comment below.</p>
]]></content:encoded>
    </item>
    
    <item>
      <title>Deploying Hugo site from Github</title>
      <link>https://www.dasmirnov.net/blog/deploying-a-hugo-site-from-github/</link>
      <pubDate>Sat, 14 Jan 2023 18:07:00 +0000</pubDate>
      
      <guid>https://www.dasmirnov.net/blog/deploying-a-hugo-site-from-github/</guid>
      <description>Just some notes on deploying a Hugo website to a server, having the server build it and then move it into the web directory, triggered by pushing a change to Github.</description>
      <content:encoded><![CDATA[<p>Just some quick notes on this - as everytime I setup a new server I forget some steps!</p>
<ol>
<li>Stick the Hugo executable somewhere on the server.</li>
<li>Use the following PHP deploy script from <a href="https://gist.github.com/cferdinandi/e6e4e05c4b25e322db4eb1f1998523ac">here</a>, published below in case it ever goes offline.</li>
</ol>
<pre tabindex="0"><code>	/**
	 * Automated deploy from GitHub
	 *
	 * https://developer.github.com/webhooks/
	 * Template from ServerPilot (https://serverpilot.io/community/articles/how-to-automatically-deploy-a-git-repo-from-bitbucket.html)
	 * Hash validation from Craig Blanchette (http://isometriks.com/verify-github-webhooks-with-php)
	 */

	// Variables
	$secret = getenv(&#39;GH_DEPLOY_SECRET&#39;); # Paul note: Best to set environment variable - avoid setting here.
	$repo_dir = &#39;/home/example/git/examplerepo&#39;;
	$web_root_dir = &#39;/home/example/public_html&#39;;
	$rendered_dir = &#39;/public&#39;;
	$hugo_path = &#39;/usr/local/bin/hugo&#39;;

	// Validate hook secret
	if ($secret !== NULL) {

		// Get signature
		$hub_signature = $_SERVER[&#39;HTTP_X_HUB_SIGNATURE&#39;];

		// Make sure signature is provided
		if (!isset($hub_signature)) {
			file_put_contents(&#39;deploy.log&#39;, date(&#39;m/d/Y h:i:s a&#39;) . &#39; Error: HTTP header &#34;X-Hub-Signature&#34; is missing.&#39; . &#34;\n&#34;, FILE_APPEND);
			die(&#39;HTTP header &#34;X-Hub-Signature&#34; is missing.&#39;);
		} elseif (!extension_loaded(&#39;hash&#39;)) {
			file_put_contents(&#39;deploy.log&#39;, date(&#39;m/d/Y h:i:s a&#39;) . &#39; Error: Missing &#34;hash&#34; extension to check the secret code validity.&#39; . &#34;\n&#34;, FILE_APPEND);
			die(&#39;Missing &#34;hash&#34; extension to check the secret code validity.&#39;);
		}

		// Split signature into algorithm and hash
		list($algo, $hash) = explode(&#39;=&#39;, $hub_signature, 2);

		// Get payload
		$payload = file_get_contents(&#39;php://input&#39;);

		// Calculate hash based on payload and the secret
		$payload_hash = hash_hmac($algo, $payload, $secret);

		// Check if hashes are equivalent
		if (!hash_equals($hash, $payload_hash)) {
		    // Kill the script or do something else here.
		    file_put_contents(&#39;deploy.log&#39;, date(&#39;m/d/Y h:i:s a&#39;) . &#39; Error: Bad Secret&#39; . &#34;\n&#34;, FILE_APPEND);
		    die(&#39;Bad secret&#39;);
		}

	};

	// Parse data from GitHub hook payload
	$data = json_decode($_POST[&#39;payload&#39;]);

	$commit_message;
	if (empty($data-&gt;commits)){
		// When merging and pushing to GitHub, the commits array will be empty.
		// In this case there is no way to know what branch was pushed to, so we will do an update.
		$commit_message .= &#39;true&#39;;
	} else {
		foreach ($data-&gt;commits as $commit) {
			$commit_message .= $commit-&gt;message;
		}
	}

	if (!empty($commit_message)) {

		// Do a git checkout, run Hugo, and copy files to public directory
		exec(&#39;cd &#39; . $repo_dir . &#39; &amp;&amp; git fetch --all &amp;&amp; git reset --hard origin/master&#39;);
		exec(&#39;cd &#39; . $repo_dir . &#39; &amp;&amp; &#39; . $hugo_path);
		exec(&#39;cd &#39; . $repo_dir . &#39; &amp;&amp; cp -r &#39; . $repo_dir . $rendered_dir . &#39;/. &#39; . $web_root_dir);

		// Log the deployment
		file_put_contents(&#39;deploy.log&#39;, date(&#39;m/d/Y h:i:s a&#39;) . &#34; Deployed branch: &#34; .  $branch . &#34; Commit: &#34; . $commit_message . &#34;\n&#34;, FILE_APPEND);

	}
</code></pre><ol start="3">
<li>Create webhook and secret in Github repository.</li>
<li>Set <code>GH_DEPLOY_SECRET</code> as an environment variable for above script to use.</li>
<li>Skip for public repo, else create SSH key if needed <code>ssh-keygen -t ed25519 -C &quot;githubemail@example.com&quot;</code> and import key into your account on Github.</li>
<li>May need <code>eval &quot;$(ssh-agent -s)&quot;</code> and tell SSH to use the key <code>ssh-add /path/to/key</code>.</li>
<li>Clone the repo to your web server by running in a suitable directory <code>git clone git@github.com:you/repo.git</code> don&rsquo;t worry about username will authenticate with SSH key.</li>
<li>CD into the repo directory make sure you can run <code>git fetch --all</code>.</li>
<li>If this fails, may need to create personal access token in Github and specify it as part of the URL in <code>.git/config</code> inside the repo directory.</li>
<li>May also need to run <code>git config --global --add safe.directory /home/example/git/examplerepo</code>.</li>
<li>Check line 69 of deployment script and make sure origin/master is correct for your branch.</li>
<li>Make sure PHP process has execute permissions on Hugo, and has read/write access to repo dir and the web server <code>public_html</code> directory, as once built into <code>repodir/public</code> it will need to be copied to <code>public_html</code>.</li>
<li>Check permissions on the Hugo temp folder <code>/tmp/hugo_cache/</code>.</li>
<li>If you can see this post, it worked!</li>
</ol>
<p>Might write this up as more of an organised general tutorial one day, in the meantime feel free to drop any comments below.</p>
]]></content:encoded>
    </item>
    
    <item>
      <title>Mastodon behind an Apache reverse proxy</title>
      <link>https://www.dasmirnov.net/blog/mastodon-behind-apache-reverse-proxy/</link>
      <pubDate>Sun, 20 Nov 2022 10:46:00 +0000</pubDate>
      
      <guid>https://www.dasmirnov.net/blog/mastodon-behind-apache-reverse-proxy/</guid>
      <description>I&amp;#39;ve run across multiple people running into issues getting Mastodon to work behind an Apache reverse proxy, this is my configuration that works.</description>
      <content:encoded><![CDATA[<p>I&rsquo;ve noticed a lot of new Mastodon server admins struggling to get Mastodon, either inside or outside of Docker, to properly work behind an Apache reverse proxy. A lot of them seem to be running into &ldquo;ERR_TOO_MANY_REDIRECTS&rdquo; or &ldquo;403 Forbidden&rdquo;. As the recommended configuation is behind Nginx there isn&rsquo;t much documentation for getting this working with Apache.</p>
<p>Although I run my <a href="https://mstdn.dasmirnov.net/">main private instance</a> through Nginx, I do run an a <a href="https://mstdn.gamercast.net/">very small public instance</a> behind Apache. This is the relevent configuration under the VirtualHost on port 443:</p>
<pre><code>ProxyPreserveHost On
RequestHeader set X-Forwarded-Proto &quot;https&quot;
ProxyPass /api/v1/streaming ws://localhost:4000
ProxyPassReverse /api/v1/streaming ws://localhost:4000
ProxyPass / http://localhost:3000/
ProxyPassReverse / http://localhost:3000/
</code></pre>
<p>ProxyPreserveHost, ProxyPass, ProxyPassReverse all require mod_proxy, RequestHeader requires mod_headers. Failure to have these modules installed when configured in <code>.conf</code> will likely prevent Apache from starting.</p>
<p>I would speculate that Mastodon wants to confirm its going to an https connection, hence RequestHeader - and perhaps its getting into a redirect loop due to this, with the virtual host on 80 redirecting? And possibly 403 is because Mastodon only expects a connection from something with the same hostname, and PreserveHost needs to be set. I&rsquo;m not sure, but that would be my thinking.</p>
]]></content:encoded>
    </item>
    
    <item>
      <title>Tesco scrap free electric vehicle charging</title>
      <link>https://www.dasmirnov.net/blog/tesco-scrap-free-electric-vehicle-charging/</link>
      <pubDate>Sat, 12 Nov 2022 15:06:00 +0000</pubDate>
      
      <guid>https://www.dasmirnov.net/blog/tesco-scrap-free-electric-vehicle-charging/</guid>
      <description>Tesco introduce fees to use their electric vehicle chargers, this is what all the people that abused it get!</description>
      <content:encoded><![CDATA[<p>Tesco have introduced fees to use their electric vehicle chargers! I can finally get to the chargers on my Saturday morning grocery shop!</p>
<p>I&rsquo;ve had an electric vehicle for a couple of years now, back in the good old days there was myself and one other guy using the chargers every Saturday morning, we&rsquo;d get maybe 4 or 5 kWh of electric for free while we were there doing the shop - enough for around 20 miles of range, not a big deal but nice to have every week.  Over the last couple of years its obviously gotten busier as EV ownership has rocketed - to the point where all electric charging bays at Tesco were full, pretty much all the time.</p>
<p>Of course, mainly because they were free - paid for chargers are never that busy!</p>
<p>I had a bit of a rant on Zap Map eight months ago about people literally just abusing the chargers - they were always supposed to be for Tesco customers, so they could get a bit of free electric during their shop.</p>
<p><img loading="lazy" src="zapmap.png" alt="My thoughts on this on Zap Map review eight months ago"  />
</p>
<p>Probably since the start of this year, genuine people literally had little chance of using them for the intended purpose, at least where I live in Worthing. Things were probably slightly quieter during the week, but the temptation is always there to just plug your car in all day and leave it.</p>
<p>Anyway the 7kW chargers like at my Tesco are now 28p per kWh, frankly that&rsquo;s still a pretty good deal to a lot of people, and the people that need to use them might actually be able to now. The pikey gits that ruined it for everyone can get stuffed! 😂 I&rsquo;ll enjoy parking in the nice big EV bays again.</p>
]]></content:encoded>
    </item>
    
    <item>
      <title>Mastodon username without a subdomain</title>
      <link>https://www.dasmirnov.net/blog/mastodon-username-without-subdomain/</link>
      <pubDate>Sat, 12 Nov 2022 12:52:00 +0000</pubDate>
      
      <guid>https://www.dasmirnov.net/blog/mastodon-username-without-subdomain/</guid>
      <description>I&amp;#39;ve recently been experimenting with the best way to run a Mastodon instance, ideally without a subdomain, this is how its configured.</description>
      <content:encoded><![CDATA[<p>This week I&rsquo;ve been experimenting with getting a Mastodon instance up and running and the best way of doing this.  One of the things I&rsquo;ve wanted to do which very few instances seem to implement, is running the Mastodon instance on subdomain.domain.tld yet using name @ domain.tld for the usernames, that&rsquo;s got to be possible right?</p>
<p>Yes it is!</p>
<p>If you edit the Mastodon <code>env.production</code> file and use the following:</p>
<pre><code>LOCAL_DOMAIN=domain.tld
WEB_DOMAIN=subdomain.domain.tld
</code></pre>
<p>We&rsquo;ll also need to forward Mastodon traffic, from the domain.tld - to the subdomain, as other instances on the internet won&rsquo;t know about the subdomain, so all their traffic will need redirecting.  You can do this in Apache by using mod_rewrite, in the sites <code>.conf</code> file place:</p>
<pre><code>RewriteEngine on
RewriteRule ^/.well-known/host-meta(.*)$ https://subdomain.domain.tld/.well-known/host-meta$1 [L,R=301]
RewriteRule ^/.well-known/webfinger(.*)$ https://subdomain.domain.tld/.well-known/webfinger$1 [L,R=301]
</code></pre>
<p>That&rsquo;ll redirect all the traffic to the right place.  Using Nginx you should be able to do it by adding the below to the <code>.conf</code> file:</p>
<pre><code>location = /.well-known/host-meta {
return 301 https://subdomain.domain.tld$request_uri;
}
location = /.well-known/webfinger {
return 301 https://subdomain.domain.tld$request_uri;
}
</code></pre>
<p>Webfinger seems to be used for new versions of Mastodon - however I&rsquo;ve also forwarded host-meta in case old versions out there are still using it. I&rsquo;ve not tested this on an instance that is already running - I would assume that existing accounts will retain their original usernames, so I&rsquo;d only recommend on a new instance. Manually editing the existing usernames will likely break interactions with all other instances, breaking follows etc.</p>
]]></content:encoded>
    </item>
    
  </channel>
</rss>
