Getting permission error with rewrite rules within Azure web app
Asked Answered
T

3

5

I have a Laravel 4 based PHP application that I have successfully gotten working within an Azure web app, the only issue that I am having is when attempting to access files from example.azurewebsites.net/js/vendor/jquery.slicknav.min.js I get a "You do not have permission to view this directory or page." Response.

The folder site/wwwroot is where I place all my Laravel application files, for those not familiar with Laravel it contains four folders: app, Bootstrap, public, and vendor.

I have set the Virtual applications and directories setting in the Azure portal to map / to site\wwwroot\public and placed within the public directory a web.config file with the following content:

<?xml version="1.0" encoding="utf-8"?>
<configuration>
    <system.webServer>
        <urlCompression doDynamicCompression="true" doStaticCompression="true" dynamicCompressionBeforeCache="true"/>
        <staticContent>
            <remove fileExtension=".svg" />
            <mimeMap fileExtension=".svg" mimeType="image/svg+xml" />
            <mimeMap fileExtension=".woff" mimeType="application/font-woff" />
            <clientCache httpExpires="Sun, 29 Mar 2020 00:00:00 GMT" cacheControlMode="UseExpires" />
        </staticContent>
        <httpProtocol>
            <customHeaders>
                <add name="Strict-Transport-Security" value="max-age=31536000; includeSubDomains"/>
                <add name="Access-Control-Allow-Origin" value="*" />
                <add name="Access-Control-Allow-Headers" value="X-Requested-With,Content-Type" />
                <add name="Access-Control-Allow-Methods" value="POST,GET,OPTIONS,DELETE,PUT,PATCH" />
            </customHeaders>
        </httpProtocol>
        <rewrite>
            <rules>
                <rule name="Laravel4" stopProcessing="true">
                    <match url="^" ignoreCase="false" />
                    <conditions logicalGrouping="MatchAll">
                        <add input="{REQUEST_FILENAME}" matchType="IsDirectory" negate="true" />
                        <add input="{REQUEST_FILENAME}" matchType="IsFile" negate="true" />
                    </conditions>
                    <action type="Rewrite" url="index.php" appendQueryString="true" />
                </rule>
            </rules>
        </rewrite>    
    </system.webServer>
</configuration>

With this set up the rewrite works as expected except when the folder name includes either app, Bootstrap, public, or vendor as it does with example.azurewebsites.net/js/vendor/jquery.slicknav.min.js.

My question is how do I amend my rewrite rules to fix this issue? If I rename the folder site\wwwroot\public\js\vendor\ by adding a hyphen to the end, it will work. I have also rebooted the container multiple times.

Edit For more clarity this is my directory structure:

├─ wwwroot
│  └─ app
│  └─ bootstrap
│  ├─ public
│  │  └─ css
│  │  └─ files
│  │  └─ fonts
│  │  └─ imgs
│  │  ├─ js
│  │  │  └─ admin
│  │  │  ├─ app
│  │  │  │  └─ link-check.js
│  │  │  └─ old
│  │  │  ├─ vendor
│  │  │  │  └─ sortable.min.js
│  │  └─ less
│  │  └─ packages
│  │  └─ tmp
│  │  └─ uploads
│  └─ vendor
└─ ...

With my web.config configuration link-check.js is accessible via example.azurewebsites.net/js/app/link-check.js while sortable.min.js is not accessible via example.azurewebsites.net/js/vendor/sortable.min.js (and nothing else within the /js/vendor path is accessible).

Note: if I rename wwwroot\public\js\vendor to wwwroot\public\js\vendor- I can view sortable.min.js from example.azurewebsites.net/js/vendor-/sortable.min.js

Trial answered 3/2, 2016 at 12:40 Comment(0)
T
10

It turns out the reason for all folders with vendor in the path returning a 403 forbidden was that I had the Azure composer web app extension installed. Within the applicationHost.xdt file for that extension it sets the following rewrite:

<rewrite xdt:Transform="InsertIfMissing">
  <rules xdt:Transform="InsertIfMissing">
    <rule name="RequestBlockingRule1" xdt:Locator="Match(name)" xdt:Transform="InsertIfMissing" stopProcessing="true">
                <match url=".*" />
                <conditions>
                    <add input="{URL}" pattern="vendor/(.*)$" />
                </conditions>
                <action type="CustomResponse" statusCode="403" statusReason="Forbidden: Access is denied." statusDescription="You do not have permission to     view this directory or page using the credentials that you supplied." />
            </rule>
  </rules>
</rewrite>

For me removing the extension obviously fixed the problem, however I have a feeling that adding a <clear/> to my rewrite rules section would clear the rules set by the extension and fix the issue.

For future reference this issue was raised against the extension on 7th Nov 2015 and on the 23rd July 2015.

Below shows my amended web.config that uses <clear/> to fix the problem

<?xml version="1.0" encoding="utf-8"?>
<configuration>
    <system.webServer>
        <urlCompression doDynamicCompression="true" doStaticCompression="true" dynamicCompressionBeforeCache="true"/>
        <staticContent>
            <remove fileExtension=".svg" />
            <mimeMap fileExtension=".svg" mimeType="image/svg+xml" />
            <mimeMap fileExtension=".woff" mimeType="application/font-woff" />
            <clientCache httpExpires="Sun, 29 Mar 2020 00:00:00 GMT" cacheControlMode="UseExpires" />
        </staticContent>
        <httpProtocol>
            <customHeaders>
                <add name="Strict-Transport-Security" value="max-age=31536000; includeSubDomains"/>
                <add name="Access-Control-Allow-Origin" value="*" />
                <add name="Access-Control-Allow-Headers" value="X-Requested-With,Content-Type" />
                <add name="Access-Control-Allow-Methods" value="POST,GET,OPTIONS,DELETE,PUT,PATCH" />
            </customHeaders>
        </httpProtocol>
        <rewrite>
            <rules>
                <clear/>
                <rule name="Laravel4" stopProcessing="true">
                    <match url="^" ignoreCase="false" />
                    <conditions logicalGrouping="MatchAll">
                        <add input="{REQUEST_FILENAME}" matchType="IsDirectory" negate="true" />
                        <add input="{REQUEST_FILENAME}" matchType="IsFile" negate="true" />
                    </conditions>
                    <action type="Rewrite" url="index.php" appendQueryString="true" />
                </rule>
            </rules>
        </rewrite>    
    </system.webServer>
</configuration>
Trial answered 4/2, 2016 at 10:21 Comment(0)
T
2

You can try the following steps:

  • modify the setting in Virtual applications and directories section back to mapping / to site\wwwroot\

  • move your web.config in the public folder to the root directory which may be the site\wwwroot in your server.

  • modify the web.config content to the following content:

<?xml version="1.0" encoding="UTF-8"?>
<configuration>
    <system.webServer>
        <rewrite>
            <rules>
                <rule name="Rewrite routed access to assets(img, css, files, js, favicon)"
                  stopProcessing="true">
                    <match url="^(img|css|files|js|favicon.ico)(.*)$" />
                </rule>
                <rule name="Imported Rule 1">
                    <match url="^(.*)$" ignoreCase="false" />
                    <action type="Rewrite" url="/public/{R:1}" />
                </rule>
                <rule name="Imported Rule 2" stopProcessing="true">
                    <match url="^(.*)$" />
                    <conditions logicalGrouping="MatchAll">
                        <add input="{REQUEST_FILENAME}" 
                                matchType="IsFile" 
                                ignoreCase="false" 
                                negate="true" />
                        <add input="{REQUEST_FILENAME}" 
                                matchType="IsDirectory" 
                                ignoreCase="false" 
                                negate="true" />
                    </conditions>
                    <action type="Rewrite" url="public/index.php/{R:1}" />
                </rule>
            </rules>
        </rewrite>
    </system.webServer>
</configuration>
Then answered 4/2, 2016 at 7:26 Comment(1)
I still get the 403 error, and with that config I get additional 404 errors, which I am able to tidy up. Its the 403 permission denied on files that exist. I thought it might be because a folder called vendor exists outside of the configured virtual directory, but app and admin also do and they work. I am amending my question with my directory structure.Trial
B
1

I added clear inside of webconfig and worked for me.

<configuration>
  <system.webServer>
    <rewrite>
      <rules>
        <rule name="Imported Rule 1" stopProcessing="true">
          <match url="^(.*)/$" ignoreCase="false" />
          <conditions>
            <add input="{REQUEST_FILENAME}" matchType="IsDirectory" ignoreCase="false" negate="true" />
          </conditions>
          <action type="Redirect" redirectType="Permanent" url="/{R:1}" />
        </rule>
         <clear/>
        <rule name="Imported Rule 2" stopProcessing="true">
          <match url="^" ignoreCase="false" />
          <conditions>
            <add input="{REQUEST_FILENAME}" matchType="IsDirectory" ignoreCase="false" negate="true" />
            <add input="{REQUEST_FILENAME}" matchType="IsFile" ignoreCase="false" negate="true" />
          </conditions>
          <action type="Rewrite" url="index.php" />
        </rule>
      </rules>
    </rewrite>
  </system.webServer>
</configuration>
Budbudapest answered 17/8, 2021 at 13:13 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.