<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Hugh Wells</title>
    <description>The latest articles on DEV Community by Hugh Wells (@crablab).</description>
    <link>https://dev.to/crablab</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F391260%2F496774fa-121c-4dd7-95f9-7814a159edc2.jpeg</url>
      <title>DEV Community: Hugh Wells</title>
      <link>https://dev.to/crablab</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/crablab"/>
    <language>en</language>
    <item>
      <title>Shipping Swag 📦</title>
      <dc:creator>Hugh Wells</dc:creator>
      <pubDate>Fri, 01 Jan 2021 19:13:31 +0000</pubDate>
      <link>https://dev.to/crablab/shipping-swag-1hni</link>
      <guid>https://dev.to/crablab/shipping-swag-1hni</guid>
      <description>&lt;p&gt;Hey y'all! &lt;/p&gt;

&lt;p&gt;I've decided to start off 2021 with a little project. Throughout 2020 I shipped a tonne of swag to attendees for hackathons and events alike. &lt;/p&gt;

&lt;p&gt;So for all you hackathon organisers, I've put together swagshiphack.dev for all your swag distribution needs 🙌&lt;/p&gt;

&lt;p&gt;Feel free to ping me an email if you'd like any help making your online event that little bit more awesome 💯&lt;/p&gt;

</description>
    </item>
    <item>
      <title>Shipping stickers for You Got This 2020: From Home</title>
      <dc:creator>Hugh Wells</dc:creator>
      <pubDate>Mon, 31 Aug 2020 20:32:27 +0000</pubDate>
      <link>https://dev.to/yougotthisconf/shipping-stickers-for-you-got-this-2020-from-home-6m8</link>
      <guid>https://dev.to/yougotthisconf/shipping-stickers-for-you-got-this-2020-from-home-6m8</guid>
      <description>&lt;p&gt;&lt;a href="https://yougotthis.io/"&gt;You Got This&lt;/a&gt; is a community conference series which focuses on the non-technical, often emotionally-labourious skills needed to be successful at work. In June, they ran their first online conference - &lt;a href="https://home.yougotthis.io"&gt;You Got This From Home&lt;/a&gt;. They decided to provide a little sticker joy to all attendees during these tough times, and collected addresses during sign up for those that wanted a little surprise to arrive on their doorstep. &lt;/p&gt;


&lt;blockquote class="ltag__twitter-tweet"&gt;
      &lt;div class="ltag__twitter-tweet__media"&gt;
        &lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--WsVoIXjf--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://pbs.twimg.com/media/EdrzPKvXkAEBB8k.jpg" alt="unknown tweet media content"&gt;
      &lt;/div&gt;

  &lt;div class="ltag__twitter-tweet__main"&gt;
    &lt;div class="ltag__twitter-tweet__header"&gt;
      &lt;img class="ltag__twitter-tweet__profile-image" src="https://res.cloudinary.com/practicaldev/image/fetch/s--UFiGxSi6--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://pbs.twimg.com/profile_images/1220049703024369668/oSSshSk2_normal.jpg" alt="Coco Chan profile image"&gt;
      &lt;div class="ltag__twitter-tweet__full-name"&gt;
        Coco Chan
      &lt;/div&gt;
      &lt;div class="ltag__twitter-tweet__username"&gt;
        @_crmzchan_
      &lt;/div&gt;
      &lt;div class="ltag__twitter-tweet__twitter-logo"&gt;
        &lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--P4t6ys1m--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://practicaldev-herokuapp-com.freetls.fastly.net/assets/twitter-f95605061196010f91e64806688390eb1a4dbc9e913682e043eb8b1e06ca484f.svg" alt="twitter logo"&gt;
      &lt;/div&gt;
    &lt;/div&gt;
    &lt;div class="ltag__twitter-tweet__body"&gt;
      Happy mail! 📮😍&lt;br&gt;&lt;br&gt;Thank you &lt;a href="https://twitter.com/yougotthisconf"&gt;@yougotthisconf&lt;/a&gt; &lt;a href="https://twitter.com/crablabuk"&gt;@crablabuk&lt;/a&gt; 
    &lt;/div&gt;
    &lt;div class="ltag__twitter-tweet__date"&gt;
      10:24 AM - 24 Jul 2020
    &lt;/div&gt;


    &lt;div class="ltag__twitter-tweet__actions"&gt;
      &lt;a href="https://twitter.com/intent/tweet?in_reply_to=1286608091958652929" class="ltag__twitter-tweet__actions__button"&gt;
        &lt;img src="https://practicaldev-herokuapp-com.freetls.fastly.net/assets/twitter-reply-action.svg" alt="Twitter reply action"&gt;
      &lt;/a&gt;
      &lt;a href="https://twitter.com/intent/retweet?tweet_id=1286608091958652929" class="ltag__twitter-tweet__actions__button"&gt;
        &lt;img src="https://practicaldev-herokuapp-com.freetls.fastly.net/assets/twitter-retweet-action.svg" alt="Twitter retweet action"&gt;
      &lt;/a&gt;
      0
      &lt;a href="https://twitter.com/intent/like?tweet_id=1286608091958652929" class="ltag__twitter-tweet__actions__button"&gt;
        &lt;img src="https://practicaldev-herokuapp-com.freetls.fastly.net/assets/twitter-like-action.svg" alt="Twitter like action"&gt;
      &lt;/a&gt;
      2
    &lt;/div&gt;
  &lt;/div&gt;
&lt;/blockquote&gt;


&lt;p&gt;The event was run by Shy and Kevin, and while Shy handled the sticker distribution throughout the Americas, I was the person who handled all of the shipments across Europe and Asia. Shipping 300 sets of stickers gave me a good excuse to (potentially) overengineer a solution to make it happen, and here's how it went down...&lt;/p&gt;

&lt;h2&gt;
  
  
  Sanitizing Data
&lt;/h2&gt;

&lt;p&gt;First step was to sanitise the address data. This had already been sorted by country and region via &lt;a href="https://smartystreets.com/"&gt;SmartyStreet's API&lt;/a&gt; and the data looked like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight plaintext"&gt;&lt;code&gt;id,full_name,address,country,region
51,The Queen,"Buckingham Palace, London, SW1A 1AA, UK",UK,EU
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;The first thing to note is the address is (usually) comma delimited. Some people used full stops (others didn't use anything!) but most used commas to indicate each line of their address. As the plan was to put this through a mail merge, the first thing was to replace these commas with line breaks (I used Python):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="nn"&gt;csv&lt;/span&gt;
&lt;span class="k"&gt;with&lt;/span&gt; &lt;span class="nb"&gt;open&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;'data.csv'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;newline&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s"&gt;''&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;as&lt;/span&gt; &lt;span class="n"&gt;csvfile&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
    &lt;span class="n"&gt;reader&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;csv&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;DictReader&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;csvfile&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

    &lt;span class="k"&gt;with&lt;/span&gt; &lt;span class="nb"&gt;open&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;'output.csv'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;'w'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;newline&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s"&gt;''&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;as&lt;/span&gt; &lt;span class="n"&gt;savefile&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="n"&gt;writer&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;csv&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;DictWriter&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;savefile&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fieldnames&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;reader&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;fieldnames&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="n"&gt;writer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;writeheader&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;

        &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;row&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;reader&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
            &lt;span class="n"&gt;row&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s"&gt;'address'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;row&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s"&gt;'address'&lt;/span&gt;&lt;span class="p"&gt;].&lt;/span&gt;&lt;span class="n"&gt;replace&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;','&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;'&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="n"&gt;writer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;writerow&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;row&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;This did what you'd expect, and replaced any "," characters in the address field with "\n". &lt;/p&gt;

&lt;h2&gt;
  
  
  Preparing Envelopes
&lt;/h2&gt;

&lt;p&gt;Next step was to design a template to directly print onto the envelopes. Since Linux and OSS rocks, we're using LibreOffice here. Kevin came up with a beautiful design:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--4HSfvYqu--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/gtmh6vgxiiau69de54ua.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--4HSfvYqu--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/gtmh6vgxiiau69de54ua.png" alt="Envelope design with YGT branding"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Once we've selected our document size with &lt;strong&gt;Format -&amp;gt; Page Style&lt;/strong&gt; and selected C6 (the size Kevin's design was for), we can then insert some placeholders for the data we're going to mail merge:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--pHZaH1Qk--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/bmp5b7zdzgpmfxn6t0h7.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--pHZaH1Qk--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/bmp5b7zdzgpmfxn6t0h7.png" alt="Envelope design with some text placeholders overlaid"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;You might think those are text boxes, but they're not! LibreOffice cannot mail merge data into textboxes, so these use a LibreOffice concept called &lt;a href="https://help.libreoffice.org/4.3/Writer/Frame"&gt;frames&lt;/a&gt;. You can place these via &lt;strong&gt;Insert -&amp;gt; Frame -&amp;gt; Frame Interactively&lt;/strong&gt;, and then dragging out the frame like a textbox. It will have a border by default but by with &lt;strong&gt;Right Click -&amp;gt; Properties&lt;/strong&gt;, you can customise this:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--LAvNgQLk--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/7qwl7jpspa3679zz762b.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--LAvNgQLk--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/7qwl7jpspa3679zz762b.png" alt="Window showing border customisation options"&gt;&lt;/a&gt; &lt;/p&gt;

&lt;p&gt;Once completed, you can modify text within the frame as normal (eg. font, colour, size etc). &lt;/p&gt;

&lt;p&gt;If you are using LibreOffice as installed by default on a Linux distro, it's likely you won't have their database package, Base, installed. With apt you need to type &lt;code&gt;sudo apt install libreoffice&lt;/code&gt; to get the all the missing components. (You can install just Base, but it does have a few dependencies you'll need to install as well). &lt;/p&gt;

&lt;p&gt;You will also be likely missing the database engine Base needs (you will later get "General input/output error" when trying to interact with a database). This is also installable via apt: &lt;code&gt;sudo apt install libreoffice-sdbc-hsqldb&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Importing our CSV into Base is a bit weird (you can't directly use a CSV to mail merge). &lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Open Base and create a new database
&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--J7JHEcFy--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/y0wrr6alru18vh8zbkv6.png" alt="Menu to create a new database"&gt;
&lt;/li&gt;
&lt;li&gt;You do want Base to "register" the database (this makes it available to other LibreOffice applications automatically), and by clicking Finish you should be promped to save it 
&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--kEu1fVi4--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/l8vgoyuqdas6bvigtjkx.png" alt="Options to configure the database"&gt;
&lt;/li&gt;
&lt;li&gt;You should now have the database open in Base. You now open your CSV alongside it in Calc
&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--t2rMBHrh--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/0ob0pwx2inylanswck1s.png" alt="Spreadsheet of data alongside database instance"&gt;
&lt;/li&gt;
&lt;li&gt;You now select all your data and copy it to your clipboard. In Base you go to &lt;strong&gt;Edit -&amp;gt; Paste&lt;/strong&gt; and a menu will appear!
&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--8EQ1x7Kw--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/5iu02k61w8w1euo7j4k9.png" alt="Menu offering to create a new table"&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;The rest is fairly self-explanatory. You will need to create a new primary key field (which Base will autoincrement for you) - I wasn't able to get it to accept the existing one. &lt;/p&gt;

&lt;p&gt;Going back to you LibreOffice Writer template, by selecting &lt;strong&gt;View -&amp;gt; Data Sources&lt;/strong&gt; you will now see your database you just created:&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--S9ZkIK5q--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/fouqrnxwv9yc86ir8rb4.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--S9ZkIK5q--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/fouqrnxwv9yc86ir8rb4.png" alt="The database displayed with the template"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Drag on the column names, and drop into your frames where you'd like that column to appear:&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--PQarRfxe--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/6hz1l06qhiqjb087es55.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--PQarRfxe--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/6hz1l06qhiqjb087es55.png" alt="Template with placeholders referencing data columns"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Phew. Almost there. &lt;/p&gt;
&lt;h2&gt;
  
  
  Printing Envelopes
&lt;/h2&gt;

&lt;p&gt;Use the standard print dialogue in LibreOffice and select &lt;strong&gt;Yes&lt;/strong&gt; when it asks if you want to print a form letter. I did try printing directly to the printer from LibreOffice but it crashed during the process, however small I made the job. &lt;/p&gt;

&lt;p&gt;However, you can instead ask LibreOffice to merge the data to individual files; I chose PDFs: &lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--7OGHZWEf--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/2594frog4bhoxnc0ql1o.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--7OGHZWEf--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/2594frog4bhoxnc0ql1o.png" alt="Print dialogue configured to print to individual PDFs"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Depending how big your database is, LibreOffice will think for a while. You'll find some very nice looking envelopes in your destination folder:&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--WiiX1ha6--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/01ea0r747guyycdf8od2.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--WiiX1ha6--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/01ea0r747guyycdf8od2.png" alt="Envelope with merged data"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;(spot the error: I didn't run the line break script on this CSV)&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;I then wrote a little Bash script to queue all the PDFs for printing:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="o"&gt;((&lt;/span&gt;&lt;span class="nv"&gt;i&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;1&lt;span class="p"&gt;;&lt;/span&gt;i&amp;lt;&lt;span class="o"&gt;=&lt;/span&gt;278&lt;span class="p"&gt;;&lt;/span&gt;i++&lt;span class="o"&gt;))&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;do
    &lt;/span&gt;lp &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="nv"&gt;$i&lt;/span&gt;&lt;span class="s2"&gt;.pdf"&lt;/span&gt;
&lt;span class="k"&gt;done&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;And you'll just need to sit and wait then! It took around 4 hours to print all 278 envelopes on an HP inkjet. You can then use your database to query how many of each region you're sending to, which is useful when buying stamps (we were going to use a franking machine, but it broke). &lt;/p&gt;

&lt;p&gt;Then time to stuff all those envelopes and stick very expensive special stickers (aka stamps) on the front!&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--7rLmscgg--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/rsjl36pb0ps2983sxhf8.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--7rLmscgg--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/rsjl36pb0ps2983sxhf8.jpeg" alt="Stamps and airmail stickers"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I hope you enjoy your stickers, and I also hope this guide is helpful to anyone else using LibreOffice for mailmerge :-) &lt;/p&gt;

&lt;p&gt;~ Hugh&lt;/p&gt;


&lt;blockquote class="ltag__twitter-tweet"&gt;
      &lt;div class="ltag__twitter-tweet__media"&gt;
        &lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--nS1Tr5sm--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://pbs.twimg.com/media/EeGYufHWoAE0XZE.jpg" alt="unknown tweet media content"&gt;
      &lt;/div&gt;

  &lt;div class="ltag__twitter-tweet__main"&gt;
    &lt;div class="ltag__twitter-tweet__header"&gt;
      &lt;img class="ltag__twitter-tweet__profile-image" src="https://res.cloudinary.com/practicaldev/image/fetch/s--axuaX0h---/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://pbs.twimg.com/profile_images/1281200111008260097/V23wjLo4_normal.png" alt="Jodie profile image"&gt;
      &lt;div class="ltag__twitter-tweet__full-name"&gt;
        Jodie
      &lt;/div&gt;
      &lt;div class="ltag__twitter-tweet__username"&gt;
        @jodieneville
      &lt;/div&gt;
      &lt;div class="ltag__twitter-tweet__twitter-logo"&gt;
        &lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--P4t6ys1m--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://practicaldev-herokuapp-com.freetls.fastly.net/assets/twitter-f95605061196010f91e64806688390eb1a4dbc9e913682e043eb8b1e06ca484f.svg" alt="twitter logo"&gt;
      &lt;/div&gt;
    &lt;/div&gt;
    &lt;div class="ltag__twitter-tweet__body"&gt;
      Thank you for my stickers &lt;a href="https://twitter.com/yougotthisconf"&gt;@yougotthisconf&lt;/a&gt; 👨‍🚀🤜 
    &lt;/div&gt;
    &lt;div class="ltag__twitter-tweet__date"&gt;
      14:18 PM - 29 Jul 2020
    &lt;/div&gt;


    &lt;div class="ltag__twitter-tweet__actions"&gt;
      &lt;a href="https://twitter.com/intent/tweet?in_reply_to=1288478895377977344" class="ltag__twitter-tweet__actions__button"&gt;
        &lt;img src="https://practicaldev-herokuapp-com.freetls.fastly.net/assets/twitter-reply-action.svg" alt="Twitter reply action"&gt;
      &lt;/a&gt;
      &lt;a href="https://twitter.com/intent/retweet?tweet_id=1288478895377977344" class="ltag__twitter-tweet__actions__button"&gt;
        &lt;img src="https://practicaldev-herokuapp-com.freetls.fastly.net/assets/twitter-retweet-action.svg" alt="Twitter retweet action"&gt;
      &lt;/a&gt;
      0
      &lt;a href="https://twitter.com/intent/like?tweet_id=1288478895377977344" class="ltag__twitter-tweet__actions__button"&gt;
        &lt;img src="https://practicaldev-herokuapp-com.freetls.fastly.net/assets/twitter-like-action.svg" alt="Twitter like action"&gt;
      &lt;/a&gt;
      6
    &lt;/div&gt;
  &lt;/div&gt;
&lt;/blockquote&gt;


&lt;p&gt;PS. You're incredibly welcome. I had a lot of fun doing it! &lt;/p&gt;

</description>
    </item>
    <item>
      <title>glitchlock with Wayland</title>
      <dc:creator>Hugh Wells</dc:creator>
      <pubDate>Sat, 25 Jul 2020 15:29:04 +0000</pubDate>
      <link>https://dev.to/crablab/glitchlock-with-wayland-3i1h</link>
      <guid>https://dev.to/crablab/glitchlock-with-wayland-3i1h</guid>
      <description>&lt;p&gt;I have created a fork of the popular glitchlock script (which used i3lock and i3lock-color) to work with swaylock in Wayland. &lt;/p&gt;

&lt;p&gt;&lt;a href="https://github.com/crablab/glitchlock"&gt;https://github.com/crablab/glitchlock&lt;/a&gt;&lt;/p&gt;

</description>
      <category>linux</category>
    </item>
    <item>
      <title>Using YouTube Subtitles for a drinking game</title>
      <dc:creator>Hugh Wells</dc:creator>
      <pubDate>Wed, 20 May 2020 20:30:15 +0000</pubDate>
      <link>https://dev.to/crablab/using-youtube-subtitles-for-a-drinking-game-5081</link>
      <guid>https://dev.to/crablab/using-youtube-subtitles-for-a-drinking-game-5081</guid>
      <description>&lt;h2&gt;
  
  
  YouTube Subtitles
&lt;/h2&gt;

&lt;p&gt;A friend suggested this concept, and I was sufficiently bored of revision to make a quick MVP. &lt;/p&gt;

&lt;p&gt;The idea is that you take a selection of videos from your favourite YouTuber and analyse their most used phrases; which you must drink on, each time someone says them. &lt;/p&gt;

&lt;h2&gt;
  
  
  Link to Code
&lt;/h2&gt;


&lt;div class="ltag-github-readme-tag"&gt;
  &lt;div class="readme-overview"&gt;
    &lt;h2&gt;
      &lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--vWogaON8--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://practicaldev-herokuapp-com.freetls.fastly.net/assets/github-logo-28d89282e0daa1e2496205e2f218a44c755b0dd6536bbadf5ed5a44a7ca54716.svg" alt="GitHub logo"&gt;
      &lt;a href="https://github.com/crablab"&gt;
        crablab
      &lt;/a&gt; / &lt;a href="https://github.com/crablab/youtube-subtitles"&gt;
        youtube-subtitles
      &lt;/a&gt;
    &lt;/h2&gt;
    &lt;h3&gt;
      
    &lt;/h3&gt;
  &lt;/div&gt;
  &lt;div class="ltag-github-body"&gt;
    
&lt;div id="readme" class="md"&gt;
&lt;h1&gt;
youtube-subtitles&lt;/h1&gt;
&lt;p&gt;A Python CLI application which will extract the most common phrases from video subtitles, and present them to you.&lt;/p&gt;
&lt;p&gt;Probably most useful as an amusing game.&lt;/p&gt;
&lt;h2&gt;
Installation&lt;/h2&gt;
&lt;p&gt;Requires:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Python3&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Try running it, if you're missing any packages then just install them with &lt;code&gt;pip&lt;/code&gt;. Apologies for no &lt;code&gt;pipenv&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;Setup:&lt;/p&gt;
&lt;p&gt;Create a &lt;code&gt;.env&lt;/code&gt; in the repository root with the following values:&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;YOUTUBE_KEY={Your YouTube API key}
CLIENT_ID={Your YouTube OAuth2 Client ID}
CLIENT_SECRET={Your YouTube OAuth2 Client Secret}
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;You'll need to go to cloud.google.com and enable the YouTube Data API where you can then generate these values.&lt;/p&gt;
&lt;p&gt;Note: the permissions scope required is &lt;code&gt;https://www.googleapis.com/auth/youtube.force-ssl&lt;/code&gt;&lt;/p&gt;
&lt;h2&gt;
Useage&lt;/h2&gt;
&lt;p&gt;Run with &lt;code&gt;python3 main.py&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;Copy and paste URLs to YouTube videos. Supply a null value to perform the analysis.&lt;/p&gt;
&lt;p&gt;Try to include as many of the outputted phrases as possible, in normal conversation.&lt;/p&gt;
&lt;h2&gt;
Future&lt;/h2&gt;
&lt;p&gt;This was a Sunday afternoon project - don't expect miracles.&lt;/p&gt;
&lt;p&gt;I might:&lt;/p&gt;
&lt;ul&gt;&lt;li&gt;…&lt;/li&gt;&lt;/ul&gt;
&lt;/div&gt;
  &lt;/div&gt;
  &lt;div class="gh-btn-container"&gt;&lt;a class="gh-btn" href="https://github.com/crablab/youtube-subtitles"&gt;View on GitHub&lt;/a&gt;&lt;/div&gt;
&lt;/div&gt;


&lt;h2&gt;
  
  
  How I built it
&lt;/h2&gt;

&lt;p&gt;This is a simple Python 3 application you can run at home. I might make it into an actual website at some point. &lt;/p&gt;

&lt;p&gt;Issues:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;It uses up a stonking great chunk of YouTube "quota". There are some small tweaks I could make to improve this: better filtering the subtitle tracks before downloading them etc. &lt;/li&gt;
&lt;li&gt;The text analysis is a very basic moving window frequency analysis. It is not clever and contains no AI or ML! Room for improvement. &lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>octograd2020</category>
    </item>
  </channel>
</rss>
