cancel
Showing results for 
Search instead for 
Did you mean: 
cancel
1917
Views
5
Helpful
3
Replies

NCS 5.3: preflight request Unauthorized (HTTP401)

nueasaks
Cisco Employee
Cisco Employee

Hi Guys,

I found the problem while developing web front-end with javascript to make a request to NSO northbound API.
Due to CORS(Cross-Origin Resource Sharing) mechanism browser will sent a preflight request to NSO before the main request.

So, In NCS version 5.2 it working fine by adding CORS header in ncs.conf under <restconf>, But after changed the version from 5.2 TO 5.3 (with same ncs.conf). It seem like NSO northbound API reply back 401 Unauthorized to the preflight request.

I also tried to debug it with packet capture and here is the capture.
this tcpstream i got in version 5.3:

### this is the response in ncs 5.3  ####
<preflight request>
OPTIONS /restconf/data/tailf-ncs:devices/device HTTP/1.1
Host: 127.0.0.1:8080
Connection: keep-alive
Accept: */*
Access-Control-Request-Method: GET
Access-Control-Request-Headers: authorization
Origin: http://localhost:3000
Sec-Fetch-Mode: cors
Sec-Fetch-Site: cross-site
Sec-Fetch-Dest: empty
Referer: http://localhost:3000/service/new

<401 error response>
HTTP/1.1 401 Unauthorized
Date: Sun, 03 May 2020 13:43:34 GMT
Content-Length: 169
Content-Type: application/yang-data+xml
WWW-Authenticate: Basic realm="restconf"
Content-Security-Policy: default-src 'self'; block-all-mixed-content; base-uri 'self'; frame-ancestors 'none';
Strict-Transport-Security: max-age=15552000; includeSubDomains
X-Content-Type-Options: nosniff
X-Frame-Options: DENY
X-XSS-Protection: 1; mode=block

<errors xmlns="urn:ietf:params:xml:ns:yang:ietf-restconf">
  <error>
    <error-tag>access-denied</error-tag>
    <error-type>protocol</error-type>
  </error>
</errors>

As i'm understanding broswer will not send any Authorization/Credential in the preflight request header by default.
NOTE : I tried to request it manually by postman, it working fine and got CORS header back in the response.

compare to the mechanism in ncs 5.2 :

### this is the response in ncs 5.2   ####
<preflight request>
OPTIONS /restconf/data/tailf-ncs:devices/device HTTP/1.1
Host: 127.0.0.1:8080
Connection: keep-alive
Accept: */*
Access-Control-Request-Method: GET
Access-Control-Request-Headers: authorization
Origin: http://localhost:3000
Sec-Fetch-Mode: cors
Sec-Fetch-Site: cross-site
....<snippet output>
<respose with cors header permission>
HTTP/1.1 200 OK
Date: Sun, 03 May 2020 13:29:46 GMT
Allow: DELETE, GET, HEAD, PATCH, POST, PUT, OPTIONS
Cache-Control: private, no-cache, must-revalidate, proxy-revalidate
Content-Length: 0
Content-Type: text/html
Accept-Patch: application/yang-data+xml, application/yang-data+json
Access-Control-Allow-Headers: Accept, Content-Type, Authorization, Accept-Encoding, Host, Origin, Content-Encoding, X-PING, X-PINGOTHER
Access-Control-Allow-Credentials: true
Access-Control-Allow-Methods: GET, HEAD, POST, PUT, PATCH, DELETE, OPTIONS
Access-Control-Allow-Origin: *
....<snippet output>
<actual request with Authorization>
GET /restconf/data/tailf-ncs:devices/device HTTP/1.1
Host: 127.0.0.1:8080
Connection: keep-alive
Accept: application/yang-data+json
Authorization: Basic YWRtaW46YWRtaW4=
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_4) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/81.0.4044.129 Safari/537.36
Origin: http://localhost:3000
Sec-Fetch-Site: cross-site
Sec-Fetch-Mode: cors
Sec-Fetch-Dest: empty
Referer: http://localhost:3000/service/new
....<snippet output>
<response>
HTTP/1.1 200 OK
Date: Sun, 03 May 2020 13:29:46 GMT
Last-Modified: Fri, 13 Mar 2020 04:00:54 GMT
Cache-Control: private, no-cache, must-revalidate, proxy-revalidate
Etag: "1584-43963-840187"
Content-Type: application/yang-data+json
Transfer-Encoding: chunked
Access-Control-Allow-Headers: Accept, Content-Type, Authorization, Accept-Encoding, Host, Origin, Content-Encoding, X-PING, X-PINGOTHER
Access-Control-Allow-Credentials: true
Access-Control-Allow-Methods: GET, HEAD, POST, PUT, PATCH, DELETE, OPTIONS
Access-Control-Allow-Origin: *
Pragma: no-cache

100F
{
  "tailf-ncs:device": [
    {
      "name": "acc1",
      "address": "127.0.0.1",
      "port": 10026,
      "ssh": {
        "host-key": [
          {
....<snippet output>


I also implement an workaround by creating nginx-reverse-proxy to handle the preflight request.
But my question is what the best solution without reverse-proxy in the middle or do i miss any additional configuration to make it working ?

Thank you so much :)

Here is config i'm using :

  <restconf>
    <enabled>true</enabled>
    <custom-headers>
     <header>
          <name>Access-Control-Allow-Origin</name>
          <value>*</value>
     </header>
     <header>
          <name>Access-Control-Allow-Methods</name>
          <value>GET, HEAD, POST, PUT, PATCH, DELETE, OPTIONS</value>
     </header>
     <header>
         <name>Access-Control-Allow-Credentials</name>
         <value>true</value>
     </header>
     <header>
          <name>Access-Control-Allow-Headers</name>
          <value>Accept, Content-Type, Authorization, Accept-Encoding, Host, Origin, Content-Encoding, X-PING, X-PINGOTHER</value>
     </header>
    </custom-headers>
  </restconf>

 

1 Accepted Solution

Accepted Solutions

perander
Cisco Employee
Cisco Employee
This was disabled (NSO versions 5.3, 5.2.2, 5.1.3, 4.7.6, 4.6.5) due to the possibility to anuathenticated poke paths for existance.
The W3C CORS standard however states that credentials should not be sent with CORS preflight check.
It is not possible to disable the credentials requirement for CORS preflight, please open a support ticket for this.

View solution in original post

3 Replies 3

perander
Cisco Employee
Cisco Employee
This was disabled (NSO versions 5.3, 5.2.2, 5.1.3, 4.7.6, 4.6.5) due to the possibility to anuathenticated poke paths for existance.
The W3C CORS standard however states that credentials should not be sent with CORS preflight check.
It is not possible to disable the credentials requirement for CORS preflight, please open a support ticket for this.

Note that it is possible to set withCredentials with XMLHttpRequest.
https://developer.mozilla.org/en-US/docs/Web/API/XMLHttpRequest/withCredentials
Unsure about browser support for similar behaviour.

Thanks for the explanation. It makes sense for disabled it because of the security concerns.
I have tried to set withCredentials flag before, but it seem to not working in firefox. Anyway I will go with reverse-proxy workaround, support case not needed for now.