<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Random Tech Posts &#8211; TristanPoulsen.com</title>
	<atom:link href="https://tristanpoulsen.com/category/random-tech-posts/feed/" rel="self" type="application/rss+xml" />
	<link>https://tristanpoulsen.com</link>
	<description>Welcome to TristanPoulsen.com</description>
	<lastBuildDate>Wed, 07 May 2025 17:38:51 +0000</lastBuildDate>
	<language>en-US</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	<generator>https://wordpress.org/?v=6.9.4</generator>

<image>
	<url>https://tristanpoulsen.com/wp-content/uploads/2024/07/cropped-Tristan-Forryst-Poulsen-initials-logo-32x32.png</url>
	<title>Random Tech Posts &#8211; TristanPoulsen.com</title>
	<link>https://tristanpoulsen.com</link>
	<width>32</width>
	<height>32</height>
</image> 
	<item>
		<title>How I Stopped Bots from Crashing My cPanel Server</title>
		<link>https://tristanpoulsen.com/how-i-stopped-bots-from-crashing-my-cpanel-server/</link>
		
		<dc:creator><![CDATA[tristanpoulsen]]></dc:creator>
		<pubDate>Wed, 07 May 2025 17:36:09 +0000</pubDate>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Random Tech Posts]]></category>
		<category><![CDATA[Strategy And Tips]]></category>
		<category><![CDATA[Tech]]></category>
		<guid isPermaLink="false">https://tristanpoulsen.com/?p=856</guid>

					<description><![CDATA[If you&#8217;re managing a cPanel + WHM server (mine runs on AlmaLinux) and notice CPU usage spiking to 100%, there&#8217;s a good chance that aggressive bots or inefficient PHP processes are hammering your server. That’s exactly what happened to me — and here’s how I fixed it. The Problem My server load was pinned at ... <a title="How I Stopped Bots from Crashing My cPanel Server" class="read-more" href="https://tristanpoulsen.com/how-i-stopped-bots-from-crashing-my-cpanel-server/" aria-label="Read more about How I Stopped Bots from Crashing My cPanel Server">Read more</a>]]></description>
										<content:encoded><![CDATA[
<p>If you&#8217;re managing a cPanel + WHM server (mine runs on AlmaLinux) and notice CPU usage spiking to 100%, there&#8217;s a good chance that <strong>aggressive bots</strong> or <strong>inefficient PHP processes</strong> are hammering your server. That’s exactly what happened to me — and here’s how I fixed it.</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">The Problem</h2>



<p>My server load was pinned at 100%, with <code>php-fpm</code> processes consuming the bulk of the CPU. Using tools like <code>htop</code> and <code>ps</code>, I traced the activity back to a few specific WordPress sites hosted on the server.</p>



<p>The common culprit? <strong>Bot traffic</strong> hammering uncached pages and XML-RPC endpoints.</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">The Fix (3-Part Solution)</h2>



<h3 class="wp-block-heading">1. <img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f9f1.png" alt="🧱" class="wp-smiley" style="height: 1em; max-height: 1em;" /> Block Bots with <code>.htaccess</code></h3>



<p>I edited the <code>.htaccess</code> file for each affected site and added rules to block known abusive bots by user agent:</p>



<pre class="wp-block-preformatted"><code># Block bad bots by user-agent<br>&lt;IfModule mod_rewrite.c><br>RewriteEngine On<br>RewriteCond %{HTTP_USER_AGENT} ^$ [OR]<br>RewriteCond %{HTTP_USER_AGENT} (semrush|ahrefs|mj12bot|dotbot|python-requests|curl|wget|masscan|sqlmap|fimap|nmap|nikto) [NC]<br>RewriteRule .* - [F,L]<br>&lt;/IfModule><br></code></pre>



<p>This simple change started deflecting unnecessary load <strong>before</strong> it could hit WordPress or PHP.</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h3 class="wp-block-heading">2. <img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f6e1.png" alt="🛡" class="wp-smiley" style="height: 1em; max-height: 1em;" /> Install and Configure Fail2Ban</h3>



<p>I installed <strong>Fail2Ban</strong> to automatically block IPs that triggered suspicious patterns in my Apache logs (like repeated bot-like requests):</p>



<pre class="wp-block-preformatted"><code>sudo yum install epel-release -y<br>sudo yum install fail2ban -y<br>sudo systemctl enable fail2ban<br>sudo systemctl start fail2ban<br></code></pre>



<p>Then, I created a jail to detect and ban bad bots:</p>



<p><strong><code>/etc/fail2ban/jail.d/apache-badbots.conf</code></strong></p>



<pre class="wp-block-preformatted"><code>[apache-badbots]<br>enabled = true<br>port    = http,https<br>filter  = apache-badbots<br>logpath = /usr/local/apache/logs/access_log<br>maxretry = 10<br>findtime = 300<br>bantime = 3600<br></code></pre>



<p><strong><code>/etc/fail2ban/filter.d/apache-badbots.conf</code></strong></p>



<pre class="wp-block-preformatted"><code>[Definition]<br>failregex = ^&lt;HOST> -.*"(GET|POST).*(crawler|bot|spider|python|curl|wget).*HTTP.*"<br></code></pre>



<p>With this in place, the server now proactively bans repeat offenders and malicious bots.</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h3 class="wp-block-heading">3. <img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f504.png" alt="🔄" class="wp-smiley" style="height: 1em; max-height: 1em;" /> Restart PHP-FPM and Apache to Flush Load</h3>



<p>Once the defenses were in place, I restarted the two main services to clear out any bloated or stuck processes:</p>



<pre class="wp-block-preformatted"><code>systemctl restart ea-php81-php-fpm<br>systemctl restart httpd<br></code></pre>



<p>This dropped my CPU usage almost instantly and gave the server a clean slate to work with.</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">Summary</h2>



<p>After these changes:</p>



<ul class="wp-block-list">
<li>CPU usage dropped from 100% to &lt;10%</li>



<li>PHP-FPM processes normalized</li>



<li>The server has stayed stable under load, even with continued traffic</li>
</ul>



<p>If you&#8217;re running cPanel/WHM and notice unexplained high load:</p>



<ul class="wp-block-list">
<li><strong>Check your access logs</strong></li>



<li><strong>Filter bots at the .htaccess level</strong></li>



<li><strong>Set up Fail2Ban to auto-ban bad actors</strong></li>



<li>And always <strong>restart PHP-FPM/Apache</strong> after config changes</li>
</ul>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>Auto Email Filter Script Python</title>
		<link>https://tristanpoulsen.com/auto-email-filter-script-python/</link>
		
		<dc:creator><![CDATA[tristanpoulsen]]></dc:creator>
		<pubDate>Wed, 21 Aug 2024 01:19:41 +0000</pubDate>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Random Tech Posts]]></category>
		<category><![CDATA[Tech]]></category>
		<guid isPermaLink="false">https://tristanpoulsen.com/?p=715</guid>

					<description><![CDATA[Today I built a python script that takes a csv file with a list of emails and using the Gmail API, moves the emails to the corresponding folder I&#8217;d like to move them to. Then it archives them. Now obviously you can do this in Gmail with an automated filter for incoming emails, so the ... <a title="Auto Email Filter Script Python" class="read-more" href="https://tristanpoulsen.com/auto-email-filter-script-python/" aria-label="Read more about Auto Email Filter Script Python">Read more</a>]]></description>
										<content:encoded><![CDATA[
<p class="has-medium-font-size">Today I built a python script that takes a csv file with a list of emails and using the Gmail API, moves the emails to the corresponding folder I&#8217;d like to move them to. Then it archives them.<br><br>Now obviously you can do this in Gmail with an automated filter for incoming emails, so the reason I&#8217;ve done this is so occasionally, probably once every other week, I&#8217;ll check all the emails in my inbox and I move emails (99% of the time to the same folders). <br>I wanted to automate this cleaning process without using <a href="https://www.sanebox.com/">SaneBox</a> and I did try to use <a href="http://make.com">Make.com</a> to do the same thing, but this was honestly simpler and I can run it without the additional operations cost.</p>



<p class="has-medium-font-size">Here&#8217;s the csv format for the headers and for the Folders &#8211; I couldn&#8217;t get it to link via the name so I have it cross-reference the Label ID to match the folders:<br>email, label<br>example_email@yahoo.com, Label_55<br><br>This is what the output looks like:</p>



<figure class="wp-block-image size-full"><img fetchpriority="high" decoding="async" width="630" height="320" src="http://3.239.168.193/wp-content/uploads/2024/08/email_filter_python_script_image-e1724203635699.png" alt="" class="wp-image-719" srcset="https://tristanpoulsen.com/wp-content/uploads/2024/08/email_filter_python_script_image-e1724203635699.png 630w, https://tristanpoulsen.com/wp-content/uploads/2024/08/email_filter_python_script_image-e1724203635699-300x152.png 300w" sizes="(max-width: 630px) 100vw, 630px" /></figure>



<div style="height:100px" aria-hidden="true" class="wp-block-spacer"></div>



<h3 class="wp-block-heading"><strong>Here&#8217;s my code if anyone wants to make their own python script:</strong></h3>



<pre class="wp-block-code"><code>import os
import pickle
import pandas as pd
import base64
from google.oauth2.credentials import Credentials
from google.auth.transport.requests import Request
from googleapiclient.discovery import build
from googleapiclient.errors import HttpError
from google_auth_oauthlib.flow import InstalledAppFlow
from email.mime.text import MIMEText
from email.mime.multipart import MIMEMultipart

# Step 1: Authentication and Service Initialization
def authenticate_gmail_api():
    SCOPES = &#91;'https://www.googleapis.com/auth/gmail.modify']
    creds = None

    if os.path.exists('token.pickle'):
        with open('token.pickle', 'rb') as token:
            creds = pickle.load(token)
    
    if not creds or not creds.valid:
        if creds and creds.expired and creds.refresh_token:
            creds.refresh(Request())
        else:
            flow = InstalledAppFlow.from_client_secrets_file(
                'credentials.json', SCOPES)
            creds = flow.run_local_server(port=0)
        with open('token.pickle', 'wb') as token:
            pickle.dump(creds, token)

    service = build('gmail', 'v1', credentials=creds)
    return service

# Step 2: Read Filters from CSV File
def read_filters_from_csv(csv_file):
    filters_df = pd.read_csv(csv_file)
    return filters_df

# Step 3: Search for Matching Emails
# Step 3: Search for Matching Emails
def search_emails(service, query):
    try:
        # Modify the query to explicitly search only within the INBOX
        query = f'label:inbox {query}'
        results = service.users().messages().list(userId='me', q=query).execute()
        messages = results.get('messages', &#91;])
        return messages
    except HttpError as error:
        print(f'An error occurred: {error}')
        return &#91;]


# Step 4: Apply Filters and Move Emails
def apply_filters(service, filters_df):
    for index, row in filters_df.iterrows():
        email_filter = row&#91;'email']
        label = row&#91;'label']

        query = f'from:{email_filter}'
        messages = search_emails(service, query)

        if not messages:
            print(f'No emails found for {email_filter}')
            continue

        for message in messages:
            msg_id = message&#91;'id']
            # Move email to the specified folder (label)
            service.users().messages().modify(
                userId='me',
                id=msg_id,
                body={'addLabelIds': &#91;label], 'removeLabelIds': &#91;'INBOX']}
            ).execute()
            print(f'Email from {email_filter} moved to {label} and archived.')

# Step 5: Retrieve and List Label IDs
def list_labels(service):
    results = service.users().labels().list(userId='me').execute()
    labels = results.get('labels', &#91;])

    if not labels:
        print('No labels found.')
    else:
        print('Labels:')
        for label in labels:
            print(f"{label&#91;'name']} - {label&#91;'id']}")

# Step 6: Main Function
def main():
    # Authenticate and create the Gmail API service
    service = authenticate_gmail_api()

    # Uncomment the line below to list all labels and their IDs
    list_labels(service)

    # Load filter rules from CSV
    csv_file = 'filters.csv'  # Replace with your CSV file
    filters_df = read_filters_from_csv(csv_file)

    # Apply filters to emails
    apply_filters(service, filters_df)

if __name__ == '__main__':
    main()
</code></pre>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>New TFP logo</title>
		<link>https://tristanpoulsen.com/new-tfp-logo/</link>
		
		<dc:creator><![CDATA[tristanpoulsen]]></dc:creator>
		<pubDate>Wed, 31 Jul 2024 19:42:42 +0000</pubDate>
				<category><![CDATA[Random Tech Posts]]></category>
		<category><![CDATA[Tech]]></category>
		<category><![CDATA[Updates]]></category>
		<guid isPermaLink="false">https://tristanpoulsen.com/?p=705</guid>

					<description><![CDATA[TFP new vs. Old I decided to add some additions to this portfolio website like the &#8220;App Ecosystems I Work With&#8221; &#38; I updated my personal logo &#8211; honestly it looks 300% better than the previous one I made over 10 years ago.. My graphic design skills have gotten better even though I&#8217;m more analytical ... <a title="New TFP logo" class="read-more" href="https://tristanpoulsen.com/new-tfp-logo/" aria-label="Read more about New TFP logo">Read more</a>]]></description>
										<content:encoded><![CDATA[		<div data-elementor-type="wp-post" data-elementor-id="705" class="elementor elementor-705" data-elementor-post-type="post">
						<section class="elementor-section elementor-top-section elementor-element elementor-element-45ea10d6 elementor-section-boxed elementor-section-height-default elementor-section-height-default" data-id="45ea10d6" data-element_type="section" data-e-type="section">
						<div class="elementor-container elementor-column-gap-default">
					<div class="elementor-column elementor-col-100 elementor-top-column elementor-element elementor-element-1b708328" data-id="1b708328" data-element_type="column" data-e-type="column">
			<div class="elementor-widget-wrap elementor-element-populated">
						<div class="elementor-element elementor-element-04268a3 elementor-widget elementor-widget-heading" data-id="04268a3" data-element_type="widget" data-e-type="widget" data-widget_type="heading.default">
				<div class="elementor-widget-container">
					<h2 class="elementor-heading-title elementor-size-default">TFP new vs. Old</h2>				</div>
				</div>
				<div class="elementor-element elementor-element-5eaa389 elementor-widget elementor-widget-text-editor" data-id="5eaa389" data-element_type="widget" data-e-type="widget" data-widget_type="text-editor.default">
				<div class="elementor-widget-container">
									
<p>I decided to add some additions to this portfolio website like the <a href="http://3.239.168.193/app-ecosystems-i-work-with/" data-type="page" data-id="593">&#8220;App Ecosystems I Work With&#8221;</a></p>

<p>&amp;</p>

<p>I updated my personal logo &#8211; honestly it looks 300% better than the previous one I made over 10 years ago.. My graphic design skills have gotten better even though I&#8217;m more analytical than creative..<br /><br />Also needed to update some image links to be served locally as the reference links I had for facebook and twitter (now X) expired or were removed.</p>
								</div>
				</div>
				<div class="elementor-element elementor-element-91d9042 uael-ba-label-hover uael-ba-halign-flex-start elementor-widget elementor-widget-uael-ba-slider" data-id="91d9042" data-element_type="widget" data-e-type="widget" data-widget_type="uael-ba-slider.default">
				<div class="elementor-widget-container">
							<div class="uael-before-after-slider">
			<div class="uael-ba-container" data-move-on-hover="yes" data-orientation="horizontal" data-offset="0.5">
				<img decoding="async" class="uael-before-img" style="position: absolute" src="https://tristanpoulsen.com/wp-content/uploads/2024/07/tfp_before_comparison-1024x1024.png" alt="Before" />
				<img decoding="async" class="uael-after-img" src="https://tristanpoulsen.com/wp-content/uploads/2024/07/Tristan-Forryst-Poulsen-initials-logo-with-buffer-1024x1024.png" alt="After" />
			</div>
		</div>
						</div>
				</div>
					</div>
		</div>
					</div>
		</section>
				</div>
		]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>Pfsense pfblockerng blocking Google and Gmail for devices on network</title>
		<link>https://tristanpoulsen.com/pfsense-pfblockerng-blocking-google-and-gmail-for-devices-on-network/</link>
		
		<dc:creator><![CDATA[tristanpoulsen]]></dc:creator>
		<pubDate>Mon, 03 Oct 2022 23:19:06 +0000</pubDate>
				<category><![CDATA[Random Tech Posts]]></category>
		<category><![CDATA[Tech]]></category>
		<guid isPermaLink="false">https://tristanpoulsen.com/?p=511</guid>

					<description><![CDATA[I&#8217;ve recently had an issue with a pfsense firewall version 2.6.0 that caused users on multiple devices to experience &#8220;connection timed out&#8221; for google.com and gmail. Youtube and other websites like bing were working fine. Ping google results in timed out, and traceroute wasn&#8217;t working either. I added google, Gmail, and youtube to the whitelist, ... <a title="Pfsense pfblockerng blocking Google and Gmail for devices on network" class="read-more" href="https://tristanpoulsen.com/pfsense-pfblockerng-blocking-google-and-gmail-for-devices-on-network/" aria-label="Read more about Pfsense pfblockerng blocking Google and Gmail for devices on network">Read more</a>]]></description>
										<content:encoded><![CDATA[
<p>I&#8217;ve recently had an issue with a pfsense firewall version 2.6.0 that caused users on multiple devices to experience &#8220;connection timed out&#8221; for google.com and gmail. Youtube and other websites like bing were working fine. Ping google results in timed out, and traceroute wasn&#8217;t working either.</p>



<p>I added google, Gmail, and youtube to the whitelist, and tested resetting DHCP and DNS. The only thing that seemed to work temporarily was to restart the pfsense device. I searched bing.com for the first time in years, also google on my phone, and none of the forums had the answer. One post on reddit even said <em>&#8220;It’s not pfsense, this is known in the industry as a layer 8 issue. <img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f61c.png" alt="😜" class="wp-smiley" style="height: 1em; max-height: 1em;" />Check pfblocker logs and look for the blocks. A note on the whitelist, sometimes you may need to clear your state table (shouldn’t have to but with any rule changes, clearing the states is a good troubleshooting thing)&#8221;</em> Reading this, I felt hopeless and went to bed.</p>



<p>The next day, I cleared the states, and nothing still. The problem this time was permanent on my desktop but periodic for other devices that were on the wifi, which confused me more. So then, by finally looking through the proper logs, I found in pfblockerng that IP&#8217;s which I crossed referenced as googles servers, were being blocked by the &#8220;Block snort2c hosts&#8221; rule in the firewall. Okay, so I searched the snort2c table to find those exact IPs from google. Finally!</p>



<p>My current solution (which is still a work in progress) was to reset the snort2c table, which for some reason had the resolved google servers for google.com on the block table. I realized that even though I had whitelisted www.google.com and google.com, they were being blocked because pfblockerng / snort2c added the resolved google IP as a block.</p>



<p>Now all I need to do is diagnose why the rule in pfblockerng is causing the snort2c block, regardless of the addition of google to the whitelist. I&#8217;ll post an update when I find the best solution vs. just resetting the snort2c table.</p>



<h2 class="wp-block-heading"><strong>Update</strong> | 10-6-2022</h2>



<p>I&#8217;ve got an update to this post and so even though pfblockerng is showing the blocked IPs from google, apparently, Suricata is to blame. Hold on, I&#8217;m no pfsense master, just a humble student of networking, I&#8217;ll get to the point.</p>



<p>After some additional research on the all-mighty google &#8211; I think I might have found a solution (still testing the viability at the moment). Seems as though the best solution is to have a modified &#8220;<strong>Remove Blocked Hosts Interval</strong>&#8221; of 1 hour.<br>&#8220;Please select the amount of time you would like hosts to be blocked. Note this setting is only applicable when using Legacy Mode blocking! This setting is ignored when using Inline IPS Mode.<br>Hint: in most cases, 1 hour is a good choice.&#8221;</p>



<p>To find this setting: <strong>Services -> Suricata -> Global Settings -> towards the bottom [<strong>Remove Blocked Hosts Interval</strong></strong>]<br>I changed mine from 4 days to 1 hour in hopes that google IPs being blocked by snort will at least be removed at a faster rate than before in my configuration.<br>I also chose to turn on logs for Suricata below the remove blocked hosts setting.</p>



<p><strong>References:</strong><br>https://forum.netgate.com/topic/131510/pfsense-keeps-blocking-google-com-i-lost-all-hope<br>https://www.reddit.com/r/PFSENSE/comments/oq4s6s/pfsense_blocking_googlecom_and_searches_but/<br>https://forum.netgate.com/topic/171592/suricata-blocking-google-gmail<br>https://www.reddit.com/r/PFSENSE/comments/qnhqvr/help_100_packet_loss_on_wan_link_not_isp_does_not/</p>



<p>***https://forum.netgate.com/topic/137889/snort/2*** Solution<br></p>
]]></content:encoded>
					
		
		
			</item>
	</channel>
</rss>
