<?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>Cisco &#8211; Jeffrey Bostoen</title>
	<atom:link href="https://jeffreybostoen.be/tag/cisco/feed/" rel="self" type="application/rss+xml" />
	<link>https://jeffreybostoen.be</link>
	<description>Freelance iTop consultant and developer - IT Consulting - Official iTop Partner</description>
	<lastBuildDate>Sat, 03 Feb 2024 10:10:17 +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://jeffreybostoen.be/wp-content/uploads/2023/01/cropped-android-chrome-512x512-1-32x32.png</url>
	<title>Cisco &#8211; Jeffrey Bostoen</title>
	<link>https://jeffreybostoen.be</link>
	<width>32</width>
	<height>32</height>
</image> 
	<item>
		<title>Duo Security API &#8211; How to test</title>
		<link>https://jeffreybostoen.be/duo-security-api-how-to-test/</link>
		
		<dc:creator><![CDATA[Jeffrey Bostoen]]></dc:creator>
		<pubDate>Sat, 03 Feb 2024 10:10:16 +0000</pubDate>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Cisco]]></category>
		<category><![CDATA[Duo]]></category>
		<category><![CDATA[Duo Security]]></category>
		<guid isPermaLink="false">https://jeffreybostoen.be/?p=1078</guid>

					<description><![CDATA[In February 2024, I had to troubleshoot an issue with a Python-based Duo implementation. There were two things I wanted to check manually, using cURL. Based on some googling, I came up with the following snippet to check if authenticating to the API worked. These resources were very helpful: Eventually, it worked and provided me [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>In February 2024, I had to troubleshoot an issue with a Python-based Duo implementation.</p>



<p>There were two things I wanted to check manually, using <strong>cURL</strong>.</p>



<p>Based on some googling, I came up with the following snippet to <strong>check if authenticating to the API worked</strong>.</p>



<p>These resources were very helpful:</p>



<ul class="wp-block-list">
<li><a href="https://duo.com/docs/authapi">Duo Auth API | Duo Security</a></li>



<li><a href="https://help.duo.com/s/article/1338?language=en_US">What are Duo&#8217;s API responses and error messages?</a> &#8211; When you need to start troubleshooting the authentication.</li>
</ul>



<pre class="wp-block-code"><code>

# Replace this with the variables found in the Duo Admin portal.
# These are generic settings.
integrationKey="xxx"
secretKey="xxx"
apiHostname="xxx.duosecurity.com"

# Endpoint specific.
method="GET"
apiPath="/auth/v2/check"
params="" # Just left this in here, in case parameters do need to be passed.

# Each request needs to be signed.
# On the web, there was a script which used \n for newlines.
# For some reason, it didn't work for me until I actually changed the template to what you see below.
# The template is used to generate a signature, and consists of five things:
# timestamp, method, API hostname, API path and parameters (if there are none, there must be a blank line.)
requestTemplate="$timestamp
$method
$apiHostname
$apiPath
$params"

timestamp=$(date -R)

signature=$(echo -n "$requestTemplate" | openssl sha1 -hmac "$integrationKey" | cut -d" " -f 2)
authHeader=$(echo -n "$integrationKey:$signature" | base64 -w0)

# Some HTTP headers must be set.
curl -s -H "Date: $timestamp" -H "Content-Type: application/x-www-form-urlencoded" -H "Authorization: Basic $authHeader" https://$apiHostname$apiPath</code></pre>



<p>Eventually, it worked and provided me with the output I needed.</p>



<p>Now, to know whether a user is authorized to log in, and (if so) returns the user&#8217;s available authentication factors, I wanted to check the <strong>/preauth</strong> endpoint. The script had to be adjusted a little bit; mainly in the cURL line. We specifically add the method in there (<strong>POST</strong>); and of course some data needed to be posted (<strong>params</strong>).</p>



<p> I struggled a while before realizing in this case I should <strong>NOT</strong> set the <strong>Content-Type: application/x-www-form-urlencoded</strong> header.</p>



<pre class="wp-block-code"><code>

# Replace this with the variables found in the Duo Admin portal.
# These are generic settings.
integrationKey="xxx"
secretKey="xxx"
apiHostname="xxx.duosecurity.com"

# Endpoint specific.
method="GET"
apiPath="/auth/v2/preauth"
params="username=xxx" # Alternative for this endpoint: user_id=xxx where xxx is a Duo user ID.

# Each request needs to be signed.
# On the web, there was a script which used \n for newlines.
# For some reason, it didn't work for me until I actually changed the template to what you see below.
# The template is used to generate a signature, and consists of five things:
# timestamp, method, API hostname, API path and parameters (if there are none, there must be a blank line.)
requestTemplate="$timestamp
$method
$apiHostname
$apiPath
$params"

timestamp=$(date -R)

signature=$(echo -n "$requestTemplate" | openssl sha1 -hmac "$integrationKey" | cut -d" " -f 2)
authHeader=$(echo -n "$integrationKey:$signature" | base64 -w0)

# Some HTTP headers must be set.
curl -s -d "$params" -H "Date: $timestamp" -H "Authorization: Basic $authHeader" -X "$method" https://$apiHostname$apiPath</code></pre>



<p>Since I only wanted to check those two things, I didn&#8217;t go through the effort of creating a function for this instead.</p>



<p></p>



<p></p>
]]></content:encoded>
					
		
		
			</item>
	</channel>
</rss>
