<?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: hunttom</title>
    <description>The latest articles on DEV Community by hunttom (@hunttom).</description>
    <link>https://dev.to/hunttom</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%2F110360%2F32d5f3de-7ac4-48cf-aba6-6c2739634fc1.png</url>
      <title>DEV Community: hunttom</title>
      <link>https://dev.to/hunttom</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/hunttom"/>
    <language>en</language>
    <item>
      <title>Adding TLS to Pi-hole</title>
      <dc:creator>hunttom</dc:creator>
      <pubDate>Mon, 01 Nov 2021 01:25:33 +0000</pubDate>
      <link>https://dev.to/hunttom/adding-tls-to-pi-hole-40gd</link>
      <guid>https://dev.to/hunttom/adding-tls-to-pi-hole-40gd</guid>
      <description>&lt;p&gt;&lt;a href="https://pi-hole.net/"&gt;PiHole&lt;/a&gt; is a great tool for blocking ads across an entire network. However, the web-based administration panel defaults to connecting to HTTP over port 80. As a network engineer, it has always bothered me that I had to pass a password into the pi-hole I've always had it on my list to update Pi-hole to use HTTPS and I could not find any documentation.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Disclaimer: configure to meet your own baseline for security standards, the examples given are generic.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h3&gt;
  
  
  Prerequisites
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;Raspberry Pi&lt;/li&gt;
&lt;li&gt;Pi-hole installed&lt;/li&gt;
&lt;li&gt;Backup of your configuration&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  Instructions
&lt;/h2&gt;

&lt;h3&gt;
  
  
  1. Create the SSL Cert:
&lt;/h3&gt;

&lt;p&gt;a. Create the self signed certificate:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;openssl req &lt;span class="nt"&gt;-new&lt;/span&gt; &lt;span class="nt"&gt;-x509&lt;/span&gt; &lt;span class="nt"&gt;-keyout&lt;/span&gt; pihole.pem &lt;span class="nt"&gt;-out&lt;/span&gt; pihole.pem &lt;span class="nt"&gt;-days&lt;/span&gt; 365 &lt;span class="nt"&gt;-nodes&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;b. Change permissions to read-only:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;chmod &lt;/span&gt;400 pihole.pem
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  2. Configure Lighttpd
&lt;/h3&gt;

&lt;p&gt;a. Create and move cert into Lighttpd:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo mkdir&lt;/span&gt; /etc/lighttpd/certs
&lt;span class="nb"&gt;mv &lt;/span&gt;pihole.pem /etc/lighttpd/certs/pihole.pem
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;b. Configure Lighttpd to accept HTTPS requests: &lt;code&gt;sudo vim /etc/lighttpd/external.conf&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;An example configuration would be for my Pi-hole DNS address at &lt;code&gt;pihole.example.com&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nv"&gt;$HTTP&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"host"&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="s2"&gt;"pihole.example.com"&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
  &lt;span class="c"&gt;# Ensure the Pi-hole Block Page knows that this is not a blocked domain&lt;/span&gt;
  setenv.add-environment &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;"fqdn"&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="s2"&gt;"true"&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;

  &lt;span class="c"&gt;# Enable the SSL engine with a LE cert, only for this specific host&lt;/span&gt;
  &lt;span class="nv"&gt;$SERVER&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"socket"&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="s2"&gt;":443"&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
    ssl.engine &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"enable"&lt;/span&gt;
    ssl.pemfile &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"/etc/lighttpd/certs/pihole.pem"&lt;/span&gt; &lt;span class="c"&gt;#Location of PEM file.&lt;/span&gt;
    ssl.use-sslv2 &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"disable"&lt;/span&gt;
    ssl.use-sslv3 &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"disable"&lt;/span&gt;       
  &lt;span class="o"&gt;}&lt;/span&gt;

  &lt;span class="c"&gt;# Redirect HTTP to HTTPS&lt;/span&gt;
  &lt;span class="nv"&gt;$HTTP&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"scheme"&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="s2"&gt;"http"&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
    &lt;span class="nv"&gt;$HTTP&lt;/span&gt;&lt;span class="o"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"host"&lt;/span&gt;&lt;span class="o"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt;~ &lt;span class="s2"&gt;".*"&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
      url.redirect &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;".*"&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="s2"&gt;"https://%0&lt;/span&gt;&lt;span class="nv"&gt;$0&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;
    &lt;span class="o"&gt;}&lt;/span&gt;
  &lt;span class="o"&gt;}&lt;/span&gt;
&lt;span class="o"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  3. Restart Lighttpd
&lt;/h2&gt;

&lt;p&gt;a. Run the command &lt;code&gt;sudo systemctl restart lighttpd&lt;/code&gt; to restart Lighttpd.&lt;/p&gt;

&lt;h2&gt;
  
  
  4. Test the configuration
&lt;/h2&gt;

&lt;p&gt;b. Log into your Pi-hole: &lt;code&gt;https://pihole.example.com&lt;/code&gt;&lt;/p&gt;

</description>
      <category>pihole</category>
      <category>security</category>
      <category>adblocking</category>
      <category>raspberrypi</category>
    </item>
    <item>
      <title>Creating Python CLI tools</title>
      <dc:creator>hunttom</dc:creator>
      <pubDate>Fri, 29 Oct 2021 04:00:14 +0000</pubDate>
      <link>https://dev.to/hunttom/creating-python-cli-scripts-13g8</link>
      <guid>https://dev.to/hunttom/creating-python-cli-scripts-13g8</guid>
      <description>&lt;p&gt;A link to the &lt;a href="https://github.com/hunttom/python_cli_skeleton"&gt;GitHub repo&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;An example using the CLI Skeleton can be found &lt;a href="https://github.com/hunttom/groundhogs_day"&gt;here&lt;/a&gt;&lt;/p&gt;

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

&lt;ol&gt;
&lt;li&gt;Python 3.6+&lt;/li&gt;
&lt;/ol&gt;

&lt;h1&gt;
  
  
  Introduction:
&lt;/h1&gt;

&lt;p&gt;Initially, I wanted to create a Python CLI tool to help automate certain aspects of my day. This tooling was inspired by me trying to use Python files when I needed to run a task such as log into a website, push code, or check the security configurations of my cloud projects. These repeated tasks were boring and distracted me from more important tasks.&lt;/p&gt;

&lt;p&gt;After reading through multiple blog posts and GitHub repositories, I found that there wasn't an clean, easy, and updated way to write a quick Python function. I wanted these scripts to be able to be called from the command line without too much effort or overhead with refactoring my code. So I decided to build a repeatable pattern that others could use.&lt;/p&gt;

&lt;h1&gt;
  
  
  The Solution:
&lt;/h1&gt;

&lt;p&gt;In the theme of October, I have created a "cli_skeleton" which will allow you to create and automate such tasks.&lt;/p&gt;

&lt;h3&gt;
  
  
  Project Layout:
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;.&lt;/span&gt;
├── cli_skeleton
│   ├── core
│   │   └── exceptions.py
│   ├── functions
│   │   └── test_function.py
│   ├── __init__.py
│   └── __main__.py
├── LICENSE
├── Makefile
├── README.md
└── setup.py
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Starting top to bottom:
&lt;/h3&gt;

&lt;h4&gt;
  
  
  Core Directory:
&lt;/h4&gt;

&lt;p&gt;Add any actions which are universal or shared actions, such as error handling that you would want to across all functions or functionality.&lt;/p&gt;

&lt;h4&gt;
  
  
  Functions:
&lt;/h4&gt;

&lt;p&gt;This directory holds your Python functions. You can have multiple functions in this directory and reference them in the &lt;code&gt;__main__.py&lt;/code&gt; file. &lt;/p&gt;

&lt;p&gt;A basic function layout is as follows:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="nn"&gt;cli_skeleton.core.exceptions&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;CLISkeletonExceptions&lt;/span&gt; 
&lt;span class="c1"&gt;# Importing all the core functions, in this instance, exceptions and error handling.
&lt;/span&gt;

&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;test_print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;test&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
&lt;span class="s"&gt;"""
The main function I want to run
"""&lt;/span&gt;
    &lt;span class="k"&gt;try&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="k"&gt;print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;test&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;except&lt;/span&gt; &lt;span class="nb"&gt;Exception&lt;/span&gt; &lt;span class="k"&gt;as&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="k"&gt;raise&lt;/span&gt; &lt;span class="n"&gt;CLISkeletonExceptions&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;str&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;
    &lt;span class="k"&gt;else&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="k"&gt;print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Successfully ran the CLI test script"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h4&gt;
  
  
  &lt;strong&gt;main&lt;/strong&gt;.py
&lt;/h4&gt;

&lt;p&gt;This Python file is the main entry point to the CLI tool. You add your logic accordingly. In the function I created, I used &lt;a href="https://docs.python.org/3/library/argparse.html"&gt;argparse&lt;/a&gt; to allow me to put arguments into the CLI tool.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="nn"&gt;cli_skeleton.functions.test_function&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;test_print&lt;/span&gt;
&lt;span class="c1"&gt;# Import the functions you want to use
&lt;/span&gt;
&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;main&lt;/span&gt;&lt;span class="p"&gt;():&lt;/span&gt;
&lt;span class="s"&gt;"""
For this example CLI script, the logic evaluates to 'True' thus running the function 'test_print' passing in 'Hi Dev.to!'
"""&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="bp"&gt;True&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;  &lt;span class="c1"&gt;# Logic for functions
&lt;/span&gt;        &lt;span class="n"&gt;test_print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Hi Dev.to!"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="c1"&gt;# The function imported from line 1.
&lt;/span&gt;
&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;__name__&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="s"&gt;'__main__'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
    &lt;span class="n"&gt;main&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h4&gt;
  
  
  Makefile
&lt;/h4&gt;

&lt;p&gt;I've included a Makefile to help various tasks such as:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;code&gt;make&lt;/code&gt; installs the tool locally&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;make uninstall&lt;/code&gt; uninstalls the tool locally&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;make venv&lt;/code&gt; creates a Python venv.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;make test&lt;/code&gt; installs and tests the tool based on a set of CLI commands. For the example I am running &lt;code&gt;cli_skeleton&lt;/code&gt; as the test&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;make clean&lt;/code&gt; removes the venv and removes all .pyc files.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Feel free to study up on Makefiles and edit to your hearts content.&lt;/p&gt;

&lt;h4&gt;
  
  
  README
&lt;/h4&gt;

&lt;p&gt;I've included a sample README&lt;/p&gt;

&lt;h4&gt;
  
  
  setup.py
&lt;/h4&gt;

&lt;p&gt;This file sets all the metadata for your Python CLI tool. &lt;br&gt;
Update accordingly.&lt;/p&gt;

&lt;h2&gt;
  
  
  Sharing and installing on different machines:
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;You can use GitHub to share/install your Python tool, run &lt;code&gt;pip3 install git+https://github.com/&amp;lt;USER&amp;gt;/&amp;lt;REPO_NAME&amp;gt;@&amp;lt;BRANCH NAME&amp;gt;&lt;/code&gt; for example: &lt;code&gt;pip3 install git+https://github.com/hunttom/cli_skeleton@main&lt;/code&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;h1&gt;
  
  
  Conclusion:
&lt;/h1&gt;

&lt;p&gt;In this post, I have covered the layout to a Python CLI tool and how to modify the files and install. I hope you can use this layout to create your own Python CLI tools! Best of luck and happy coding!&lt;/p&gt;

&lt;h2&gt;
  
  
  Additional reading/resources to help:
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;&lt;a href="https://docs.python.org/3/library/argparse.html"&gt;About Argparse&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://dev.to/matthewepler/using-makefiles-to-automate-workflows-acd"&gt;About Makefiles&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://dev.to/niklastiede/distribute-a-python-app-via-setup-py-file-4boh"&gt;About setup.py&lt;/a&gt;&lt;/li&gt;
&lt;/ol&gt;

</description>
      <category>python</category>
      <category>cli</category>
      <category>terminal</category>
    </item>
    <item>
      <title>Alfred Plugin for searching Dev.to</title>
      <dc:creator>hunttom</dc:creator>
      <pubDate>Tue, 05 Jan 2021 19:51:58 +0000</pubDate>
      <link>https://dev.to/hunttom/alfred-plugin-for-searching-dev-to-1lhp</link>
      <guid>https://dev.to/hunttom/alfred-plugin-for-searching-dev-to-1lhp</guid>
      <description>&lt;p&gt;Hey all,&lt;br&gt;
Super short post - I search Dev.to a lot. So in typical developer fashion, if you do something repetitive, automate!&lt;/p&gt;

&lt;p&gt;At the following Github repo, I posted a really quick search function in Alfred. &lt;a href="https://github.com/hunttom/bodega/blob/master/alfred/Dev.to.alfredworkflow"&gt;https://github.com/hunttom/bodega/blob/master/alfred/Dev.to.alfredworkflow&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Requires: Alfred: &lt;a href="https://www.alfredapp.com/"&gt;https://www.alfredapp.com/&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;To Use: Type "dev {search query}" to search in Dev.to. Alfred will open up in a new tab within your default browser.&lt;/p&gt;

&lt;p&gt;Enjoy!&lt;/p&gt;

&lt;p&gt;What other Alfred productivity apps do you enjoy using?&lt;/p&gt;

</description>
      <category>alfred</category>
      <category>productivity</category>
    </item>
    <item>
      <title>Programmatically setting up a Dev Environment</title>
      <dc:creator>hunttom</dc:creator>
      <pubDate>Fri, 19 Jul 2019 03:45:58 +0000</pubDate>
      <link>https://dev.to/ugw7g85q/setting-up-a-dev-environment-3njm</link>
      <guid>https://dev.to/ugw7g85q/setting-up-a-dev-environment-3njm</guid>
      <description>&lt;p&gt;So recently, due to user error (mine) I had to wipe my developer machine and go through the arduous process of setting it back up. In the attempt to simplify the process, I began searching around on the internet as a way to codify setup. After many tutorials, recommendations, and peer feedback (way too many contributors to mention: but thank you all!) I wanted to share my results. What used to take me 6 hours of set up of a new MacOS, takes about 30 minutes now (minus the cloning of my repositories and transfer of my documents, etc).&lt;/p&gt;

&lt;p&gt;If you are needing to set up a your development machine, please take this template, change, alter, and make it your own. Most of all I hope to provide a solution to a new developer, a developer who just doesn't want to reimage their machine, or just someone who wants to look at the tools I use. An updated image of this script can be found at my GitHub Repo. &lt;a href="https://github.com/hunttom/bodega/tree/master/developer_setup"&gt;Link&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Happy Coding!&lt;/p&gt;




&lt;h3&gt;
  
  
  Tools I use:
&lt;/h3&gt;

&lt;p&gt;HomeBrew&lt;br&gt;
Python3+&lt;br&gt;
Pip&lt;br&gt;
PyEnv&lt;/p&gt;

&lt;h3&gt;
  
  
  Requirements:
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;Running High Sierra&lt;/li&gt;
&lt;li&gt;Admin of your computer&lt;/li&gt;
&lt;li&gt;Understand and read every line of code and customize to your needs. THIS WILL FAIL IF YOU RUN AS IS! (Primarily the Git section, SSH Section, and what environment you work with (Python, Ruby, NodeJS, etc)).&lt;/li&gt;
&lt;li&gt;Remove the tools or sections you don't want either by commenting or deleting.&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  To install
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;Download from the &lt;a href="https://github.com/hunttom/bodega/tree/master/developer_setup"&gt;GitHub&lt;/a&gt; or copy/paste this version into a bash script.&lt;/li&gt;
&lt;li&gt;Run &lt;code&gt;bash FILE_NAME&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;Go get coffee.&lt;/li&gt;
&lt;/ol&gt;



&lt;div class="highlight"&gt;&lt;pre class="highlight plaintext"&gt;&lt;code&gt;

!/bin/bash


# Inspration was based on the following:
# See attached for how to set up a dev environment: https://www.taniarascia.com/setting-up-a-brand-new-mac-for-development/
#########################
# Creating SSH Keys  
# Install SSH Keys: ssh-keygen see documentation at https://www.ssh.com/ssh/keygen/
#########################

  #REQUIREMENTS
  # Make sure you are running High Sierra+
  # Update Location Settings in Preferences
  # Update Location Settings in Outlook
  # iTerm: Change Font to Meslo and Theme to Solarized
  # Copy (If you have any) Config Files for .ssh; .aws; .zshrc (and comment out ZSHRC section); and neofetch
  # See the bottom section if you want to Java or Ruby over Python.

#########################

# Run outstanding system updates
echo "Updating system install..."
softwareupdate -ia --verbose
echo ""

# Install xcode cli development tools
echo "Installing xcode cli development tools..."
xcode-select --install
echo ""

#####################################################################
# Install brew apps
#####################################################################

# Install homebrew
echo "Installing homebrew..."
/usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"
echo ""
echo "Installing HomeBrew apps..."
echo ""

# Dev cli apps
brew install ack                               # Faster Grep - Grep for programmers
brew install bat                               # Syntax Highlighting
brew install bench                             # Benchmarking Tool for Code
brew install openssl                           # SSL
brew install flake8                            # Python Linter
brew install fzf                               # Fuzzy String Search
brew install git                               # Version control
brew install git-secrets                       # Checks for Credential Exposure
brew install gnupg                             # GPG Suite
brew install htop                              # Performance Monitoring
brew install iftop                             # Network Monitoring
brew install libksba                           # GPG Package
brew install libyaml                           # A C library for parsing and emitting YAML
brew install mas                               # MAS Install
brew install neofetch                          # iterm Machine Description
brew install neovim                            # Modern VIM
brew install node                              # NodeJS
brew install postgresql                        # PostgreSQL and tools
brew install reattach-to-user-namespace        # Needed for clipboard integration from vim and tmux
brew install telnet                            # Telnet
brew install terraform                         # Terraform
brew install tmux                              # Terminal multiplexer
brew install tree                              # Tree Command
brew install wget                              # Retrieve web files
brew install z                                 # Jump Around based on directories

# Dev gui apps
brew cask install balenaetcher                 # Burn raspberry pi images
brew cask install caffeine                     # Keep your screen on
brew cask install cyberduck                    # SFTP Client
brew cask install docker                       # Container tooling
brew cask install drawio                       # Icon/Graphic Creator
brew cask install firefox                      # Firefox -  SignIn/Import Settings about:support. Open "Show In Finder" Copy and Replace
brew cask install gimp                         # Graphics editor
brew cask install gitup                        # Visual Git
brew cask install google-chrome                # Chrome web browser
brew cask install iterm2                       # A better terminal: change bash to /bin/bash -l in Preferences/Profile
brew cask install mountain-duck                # Drive Mounter
brew cask install postman                      # GUI for testing apis
brew cask install pycharm-ce                   # Text based IDE
brew cask install sublime-text                 # Text Editor
brew cask install vagrant                      # Virtual Boxes CLI
brew cask install veracrypt                    # Encryption Gear
brew cask install virtualbox                   # VirtualBox
brew cask install wireshark                    # Wireshark
brew cask install zenmap                       # NMAP Client

# Personal gui apps
brew install syncthing                         # Backup Software
brew services start syncthing
brew cask install hazel                        # Folder Cleanup
open /Applications/Hazel.app/
brew cask install quickhash                    # Hashing Program
brew cask install safeincloud-password-manager # Password Manager

# Communication
brew cask install quip                         # Quip for Collaboration
brew cask install riot                         # IRC Client
brew cask install signal                       # Signal


# Productivity gui apps
brew cask install alfred                       # Mac os helper
open /Applications/Alfred\ 3.app/
brew cask install flux                         # Blue light solution
open /Applications/Flux.app/


echo ""

#####################################################################
# Install mac app store apps
#
# NOTE: The mas commands will only work if you are:
#   - on High Sierra+
#   - have downloaded the app from the store previously
#   - are currently logged into the app store app
#####################################################################

echo "Installing mas cli..."
brew install mas                               # Mac App Store CLI
echo ""

echo "Installing mas apps..."
echo ""

# Dev gui apps
mas install 497799835                         # Xcode, ios/osx app dev env
sudo xcodebuild -license accept
mas install 1295203466                        # Microsoft Remote Desktop, rdp into windows
mas install 1451685025

# Work gui apps
mas install 866773894                         # Quiver PAID Notetaking

#####################################################################
# Pimp zsh
#
# NOTE: To use the bullet-train theme with zsh you will need to
# change Terminal/iterm2 to use one of the powerline fonts installed
# with the first set of commands below.
#####################################################################

# Install powerline fonts (needed by bullet train theme)
git clone https://github.com/powerline/fonts.git ~/tmp/fonts
sudo ~/tmp/fonts/install.sh
rm -rf ~/tmp/fonts

# Install bullet-train theme
# mkdir -p ~/.zsh-custom/themes
# sudo curl -L -o ~/.zsh-custom/themes/bullet-train.zsh-theme https://raw.githubusercontent.com/caiogondim/bullet-train.zsh/master/bullet-train.zsh-theme

# Install oh-my-zsh theme
if [ ! -d "$HOME/.oh-my-zsh" ]; then
  echo "Installing oh-my-zsh"
  sh -c "$(curl -fsSL https://raw.githubusercontent.com/robbyrussell/oh-my-zsh/master/tools/install.sh)"
fi

# Customise oh my zsh to use agnoster theme
sed -i -e 's/ZSH_THEME="\(.*\)"/ZSH_THEME="agnoster"/' ~/.zshrc
sed -i -e 's/^# ZSH_CUSTOM=\(.*\)/ZSH_CUSTOM=~\/.zsh-custom/' ~/.zshrc

#####################################################################
# ZSH Preferences
#####################################################################
echo 'alias upd="brew update; brew upgrade; brew cask upgrade; mas upgrade; brew cleanup --prune-prefix; brew doctor; brew cleanup;' &amp;gt;&amp;gt; ~/.zshrc
echo 'alias weather="curl wttr.in/Tarrytown:NewYork"' &amp;gt;&amp;gt; ~/.zshrc
echo 'alias gitc="git ls-files | xargs cat | wc -l"' &amp;gt;&amp;gt; ~/.zshrc
git clone https://github.com/chriskempson/base16-shell.git ~/.config/base16-shell

echo '# Base32 Shell
BASE16_SHELL="$HOME/.config/base16-shell/"
[ -n "$PS1" ] &amp;amp;&amp;amp; \
    [ -s "$BASE16_SHELL/profile_helper.sh" ] &amp;amp;&amp;amp; \
        eval "$("$BASE16_SHELL/profile_helper.sh")"' &amp;gt;&amp;gt; ~/.zshrc

source ~/.zshrc

#####################################################################
# Git Configuration
#####################################################################
echo ""
echo "Creating Git Configuration"
echo ""

touch ~/.gitconfig

cat &amp;lt;&amp;lt; EOT &amp;gt;&amp;gt; ~/.gitconfig
[user]
    name = FIRST_NAME LAST_Name
    email = EMAIL
[github]
    user = USERNAME 
[alias]
    a = add
    ca = commit -a
    cam = commit -am
    s = status
    pom = push origin master
    pog = push origin gh-pages
    puom = pull origin master
    puog = pull origin gh-pages
    cob = checkout -b
[credential]
    helper = osxkeychain
[secrets]
    providers = git secrets --aws-provider
    patterns = [A-Z0-9]{20}
    patterns = (\"|')?(AWS|aws|Aws)?_?(SECRET|secret|Secret)?_?(ACCESS|access|Access)?_?(KEY|key|Key)(\"|')?\\s*(:|=&amp;gt;|=)\\s*(\"|')?[A-Za-z0-9/\\+=]{40}(\"|')?
    patterns = (\"|')?(AWS|aws|Aws)?_?(ACCOUNT|account|Account)_?(ID|id|Id)?(\"|')?\\s*(:|=&amp;gt;|=)\\s*(\"|')?[0-9]{4}\\-?[0-9]{4}\\-?[0-9]{4}(\"|')?
    allowed = AKIAIOSFODNN7EXAMPLE
    allowed = wJalrXUtnFEMI/K7MDENG/bPxRfiCYEXAMPLEKEY
EOT

#####################################################################
# SSH Configuration
#####################################################################
echo ""
echo "Configuring SSH"
echo ""

touch ~/.ssh/config

cat &amp;lt;&amp;lt; EOT &amp;gt;&amp;gt; ~/.ssh/config
ANY SSH CONFIG INFO YOU WANT.

EOT
#####################################################################
# Creating Email Cert
#####################################################################
echo ''
echo 'go to Outlook and/or Apple Mail and configure to have "alias" cert sign all messages and encrypt(if needed)'
echo ''

#####################################################################
# Install the devtool version managers
#####################################################################

# # Install Sdkman (manage jvm related build tools)
# if [ ! -f ~/.sdkman/bin/sdkman-init.sh ]; then
#   echo "Installing Sdkman"
#   curl -s "https://get.sdkman.io" | bash
#   source ~/.sdkman/bin/sdkman-init.sh

#   sdk install java 8.0.181-zulu
#   sdk install gradle
#   sdk install maven
#   sdk install sbt
#   sdk install visualvm
# fi

# Install Node Version Manager
if [ ! -f ~/.nvm/nvm.sh ]; then
  echo "Installing Node Version Manager"
  curl -o- https://raw.githubusercontent.com/creationix/nvm/v0.34.0/install.sh | bash

  cat &amp;lt;&amp;lt; EOT &amp;gt;&amp;gt; ~/.zshrc
export NVM_DIR="$HOME/.nvm"
[ -s "$NVM_DIR/nvm.sh" ] &amp;amp;&amp;amp; \. "$NVM_DIR/nvm.sh"  # This loads nvm
[ -s "$NVM_DIR/bash_completion" ] &amp;amp;&amp;amp; \. "$NVM_DIR/bash_completion"  # This loads nvm bash_completion
EOT

  source ~/.zshrc
  nvm install node
fi

#####################################################################
# Python Installer
#####################################################################
# Python Env and Global ENV
brew install pyenv                             # Python ENV
brew install pyenv-virtualenv                  # PythonEnv VirualEnv
echo '#Python Env'
echo 'eval $(pyenv init -)"' &amp;gt;&amp;gt; ~/.zshrc
echo 'eval "$(pyenv virtualenv-init -)"' &amp;gt;&amp;gt; ~/.zshrc
exec $SHELL
pyenv
pyenv install 3.7.4
pyenv global 3.7.4
pyenv virtualenv 3.7.4 global-venv
pyenv global global-venv
pip install ansible awscli boto3 boto
source ~/.zshrc

sudo installer -pkg /Library/Developer/CommandLineTools/Packages/macOS_SDK_headers_for_macOS_10.14.pkg -target / # Install zlib for pyenv

#####################################################################
# Ruby
#####################################################################

# Install Ruby I've decided to use rbenv.
brew install rbenv
rbenv init
curl -fsSL https://github.com/rbenv/rbenv-installer/raw/master/bin/rbenv-doctor | bash
brew upgrade rbenv ruby-build
rbenv install 2.6.1
rbenv global 2.6.1
echo 'eval "$(rbenv init -)"' &amp;gt;&amp;gt; ~/.zshrc
rbenv rehash

#####################################################################
# Ruby Gems for Install
#####################################################################
gem install bundler jekyll

#####################################################################
# RVM Option
#####################################################################

# Install Ruby Version Manager if you want to use this Ruby Version Manager
# if [ ! -f ~/.rvm/scripts/rvm ]; then
#   echo "Installing RVM"
#   curl -L -o rvm-installer https://raw.github.com/wayneeseguin/rvm/master/binscripts/rvm-installer
#   chmod +x ./rvm-installer
#   ./rvm-installer
#   rm rvm-installer

#   source ~/.zshrc
#   rvm install ruby --latest --default
# fi

#####################################################################
# Configurations
#####################################################################

chflags nohidden ~/Library #Show Library
defaults write com.apple.finder AppleShowAllFiles YES #Show Hidden Files
defaults write com.apple.finder ShowPathbar -bool true #Show Path Bar
defaults write com.apple.finder ShowStatusBar -bool true #Show status Bar
defaults write com.google.Chrome AppleEnableSwipeNavigateWithScrolls -bool FALSE #Removing two finger "go back" from Chrome
defaults write com.mozilla.Firefox AppleEnableSwipeNavigateWithScrolls -bool FALSE #Removing two finder "go back" from Chrome
sudo installer -pkg /Library/Developer/CommandLineTools/Packages/macOS_SDK_headers_for_macOS_10.14.pkg -target / # Install zlib for pyenv

exec $SHELL
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

</description>
      <category>setup</category>
      <category>macos</category>
      <category>developerenviornment</category>
      <category>productive</category>
    </item>
    <item>
      <title>A Self-Service Raspberry Pi VPN</title>
      <dc:creator>hunttom</dc:creator>
      <pubDate>Fri, 12 Jul 2019 03:22:29 +0000</pubDate>
      <link>https://dev.to/ugw7g85q/a-self-service-raspberry-pi-vpn-2f45</link>
      <guid>https://dev.to/ugw7g85q/a-self-service-raspberry-pi-vpn-2f45</guid>
      <description>&lt;p&gt;Recently, I wanted to set up a VPN server residing on a Raspberry Pi on my home network and wanted to share my adventures with you. While this is more of an infrastructure and VPN-based post, I thought that it might provide some developers in need of a secure way to get back to their home networks as I did. Additionally, this is a fun way to brush up on infrastructure work and mess around with a Raspberry Pi!&lt;/p&gt;

&lt;p&gt;Here is an overview of my setup:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2F4axdzf5le26c2a3kwikw.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2F4axdzf5le26c2a3kwikw.png"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Necessary equipment:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;A Raspberry Pi (Preferable a RBP2+)&lt;/li&gt;
&lt;li&gt;An AWS account (or any other Cloud Provider) - In this post I use AWS&lt;/li&gt;
&lt;li&gt;A domain.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Problem and Context: I wanted to have a secure way to link back into my home network when traveling and using public networks. VPN Companies were an option but I wanted the following:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;The ability to update and check on my IoT projects running on my home network.&lt;/li&gt;
&lt;li&gt;Cost - VPN companies have robust servers with world-wide reach. Although, they do incur cost monthly and the RBP option was a lot cheaper (totaling around $2.80 per month) including energy and cost of the AWS hosted zone.&lt;/li&gt;
&lt;li&gt;I had a RBP laying around - why not!&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Solution: A PiVPN running on my home network allowing me to both reach my home network and the Internet. My VPN endpoint (RBP) remains online because I run a Cron job every 24 hours to update a hosted zone's A record on AWS Route53.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;I set up the RBP: updating Linux and changing the login to a very strong password (Security always!). I went a step further and only enabled PEM key login for SSH for extra security.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;I set up my router for port forwarding on a random port to my RBP.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Used the &lt;a href="http://www.pivpn.io/" rel="noopener noreferrer"&gt;PiVPN&lt;/a&gt; &lt;code&gt;curl -L https://install.pivpn.io | bash&lt;/code&gt; to generate the OpenVPN certificate and set up the OpenVPN server to my preferences.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Created the PiVPN cert and used SCP to download that cert and change the .opvn file to ensure that the endpoint was my DynamicDNS record (example: vpn.example.com).&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;To circumvent an issue I ran into where my VPN pointed to my router's public IP and my ISP changed my IP address, I modified a DynamicDNS script I found (Compliments to &lt;a href="https://willwarren.com/" rel="noopener noreferrer"&gt;https://willwarren.com/&lt;/a&gt;).&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Set up a Cron Job to query once a day and update my AWS Route53 A Record if my ISP changes my public IP address again. When SSH'ed into the the RBP run &lt;code&gt;crontab -e&lt;/code&gt; and put the desire frequency of triggering the Cron job. An easy tool to use can be found &lt;a href="https://crontab.guru/#0_1_*_*" rel="noopener noreferrer"&gt;here&lt;/a&gt;.&lt;br&gt;
Example 24 hour Cron job that runs every midnight: &lt;code&gt;0 0 * * * /bin/bash /home/pi/dynamic_dns_route53.sh&lt;/code&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Install &lt;a href="https://docs.aws.amazon.com/cli/latest/userguide/cli-chap-install.html" rel="noopener noreferrer"&gt;AWS CLI&lt;/a&gt; on the RBP.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Create an IAM User with a policy &lt;code&gt;dynamicdnspolicy&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="w"&gt;    &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"Version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"2012-10-17"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"Statement"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="w"&gt;
            &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
                &lt;/span&gt;&lt;span class="nl"&gt;"Sid"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"route53changerecord"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
                &lt;/span&gt;&lt;span class="nl"&gt;"Effect"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Allow"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
                &lt;/span&gt;&lt;span class="nl"&gt;"Action"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"route53:ChangeResourceRecordSets"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
                &lt;/span&gt;&lt;span class="nl"&gt;"Resource"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"arn:aws:route53:::hostedzone/HOSTEDZONE"&lt;/span&gt;&lt;span class="w"&gt;
            &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;&lt;p&gt;Create an Access Key/Secret key pair and add to AWS CLI profile on the RBP.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Download the &lt;a href="https://github.com/hunttom/bodega/tree/master/aws" rel="noopener noreferrer"&gt;DynamicDNS Script&lt;/a&gt; from my Repository&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Add hosted zone and record set to the &lt;code&gt;dynamic_dns_route53.sh&lt;/code&gt; script on lines 8 and 11 from Route53. &lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Verify that the script ran!&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;You can change out the script to whatever cloud/DNS provider you have!&lt;/p&gt;

&lt;p&gt;Best of success (securely of course!)&lt;/p&gt;




&lt;p&gt;PS This worked on both my phone and laptop, I just needed an OpenVPN client to use the cert!&lt;/p&gt;

</description>
      <category>aws</category>
      <category>dynamicdns</category>
      <category>vpn</category>
    </item>
  </channel>
</rss>
