title: CodeIgniter 4... documentRoot is not in public... htaccess is not working
body: <p>I am starting to dabble in CodeIgniter 4. 
  Completed a simple app. On local, I have the documentroot setup to be /public/ where as on the product hosting environment, I am unable to set the documentroot to be in /public/. </p>
  
  <p>Instead it is in /root.</p>
  
  <p>So the structure is like so:</p>
  
  <pre><code>/root
  ../admin
  ../app
  ../system
  ../public
  ../.htaccess
  ../index.php
  </code></pre>
  
  <p>I've moved the htaccess from the public folder to the root level.</p>
  
  <pre><code># Disable directory browsing
  Options All -Indexes
  
  # ----------------------------------------------------------------------
  # Rewrite engine
  # ----------------------------------------------------------------------
  
  # Turning on the rewrite engine is necessary for the following rules and features.
  # FollowSymLinks must be enabled for this to work.
  &lt;IfModule mod_rewrite.c&gt;
      Options +FollowSymlinks
      RewriteEngine On
  
      # If you installed CodeIgniter in a subfolder, you will need to
      # change the following line to match the subfolder you need.
      # http://httpd.apache.org/docs/current/mod/mod_rewrite.html#rewritebase
      RewriteBase /public
  
      # Redirect Trailing Slashes...
      RewriteCond %{REQUEST_FILENAME} !-f
      RewriteRule ^(.*)/$ /public/$1 [L,R=301]
  
      # Rewrite "www.example.com -&gt; example.com"
      RewriteCond %{HTTPS} !=on
      RewriteCond %{HTTP_HOST} ^www\.(.+)$ [NC]
      RewriteRule ^ http://%1%{REQUEST_URI} [R=301,L]
  
      # Checks to see if the user is attempting to access a valid file,
      # such as an image or css document, if this isn't true it sends the
      # request to the front controller, index.php
      RewriteCond %{REQUEST_FILENAME} !-f
      RewriteCond %{REQUEST_FILENAME} !-d
      RewriteRule ^(.*)$ index.php/$1 [L]
  
      # Ensure Authorization header is passed along
      RewriteCond %{HTTP:Authorization} .
      RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]
  &lt;/IfModule&gt;
  
  &lt;IfModule !mod_rewrite.c&gt;
      # If we don't have mod_rewrite installed, all 404's
      # can be sent to index.php, and everything works as normal.
      ErrorDocument 404 index.php
  &lt;/IfModule&gt;
  
  # Disable server signature start
      ServerSignature Off
  # Disable server signature end
  </code></pre>
  
  <p>and the index.php in root file:</p>
  
  <pre><code>&lt;?php
  
  // Valid PHP Version?
  $minPHPVersion = '7.2';
  if (phpversion() &lt; $minPHPVersion)
  {
      die("Your PHP version must be {$minPHPVersion} or higher to run CodeIgniter. Current version: " . phpversion());
  }
  unset($minPHPVersion);
  
  // Path to the front controller (this file)
  define('FCPATH', __DIR__ . DIRECTORY_SEPARATOR);
  
  // Location of the Paths config file.
  // This is the line that might need to be changed, depending on your folder structure.
  $pathsPath = FCPATH . 'app/Config/Paths.php';
  // ^^^ Change this if you move your application folder
  
  /*
   *---------------------------------------------------------------
   * BOOTSTRAP THE APPLICATION
   *---------------------------------------------------------------
   * This process sets up the path constants, loads and registers
   * our autoloader, along with Composer's, loads our constants
   * and fires up an environment-specific bootstrapping.
   */
  
  // Ensure the current directory is pointing to the front controller's directory
  chdir(__DIR__);
  
  // Load our paths config file
  require $pathsPath;
  $paths = new Config\Paths();
  
  // Location of the framework bootstrap file.
  $app = require rtrim($paths-&gt;systemDirectory, '/ ') . '/bootstrap.php';
  
  /*
   *---------------------------------------------------------------
   * LAUNCH THE APPLICATION
   *---------------------------------------------------------------
   * Now that everything is setup, it's time to actually fire
   * up the engines and make this app do its thang.
   */
  $app-&gt;run();
  </code></pre>
  
  <p>In addition, the app config file:</p>
  
  <pre><code>&lt;?php namespace Config;
  
  use CodeIgniter\Config\BaseConfig;
  
  class App extends BaseConfig
  {
  
      /*
      |--------------------------------------------------------------------------
      | Base Site URL
      |--------------------------------------------------------------------------
      |
      | URL to your CodeIgniter root. Typically this will be your base URL,
      | WITH a trailing slash:
      |
      |   http://example.com/
      |
      | If this is not set then CodeIgniter will try guess the protocol, domain
      | and path to your installation. However, you should always configure this
      | explicitly and never rely on auto-guessing, especially in production
      | environments.
      |
      */
      public $baseURL = 'http://sub.domain.com';
  
      /*
      |--------------------------------------------------------------------------
      | Index File
      |--------------------------------------------------------------------------
      |
      | Typically this will be your index.php file, unless you've renamed it to
      | something else. If you are using mod_rewrite to remove the page set this
      | variable so that it is blank.
      |
      */
      public $indexPage = 'index.php';
  
      /*
      |--------------------------------------------------------------------------
      | URI PROTOCOL
      |--------------------------------------------------------------------------
      |
      | This item determines which getServer global should be used to retrieve the
      | URI string.  The default setting of 'REQUEST_URI' works for most servers.
      | If your links do not seem to work, try one of the other delicious flavors:
      |
      | 'REQUEST_URI'    Uses $_SERVER['REQUEST_URI']
      | 'QUERY_STRING'   Uses $_SERVER['QUERY_STRING']
      | 'PATH_INFO'      Uses $_SERVER['PATH_INFO']
      |
      | WARNING: If you set this to 'PATH_INFO', URIs will always be URL-decoded!
      */
      public $uriProtocol = 'REQUEST_URI';
  
      /*
      |--------------------------------------------------------------------------
      | Default Locale
      |--------------------------------------------------------------------------
      |
      | The Locale roughly represents the language and location that your visitor
      | is viewing the site from. It affects the language strings and other
      | strings (like currency markers, numbers, etc), that your program
      | should run under for this request.
      |
      */
      public $defaultLocale = 'en';
  
      /*
      |--------------------------------------------------------------------------
      | Negotiate Locale
      |--------------------------------------------------------------------------
      |
      | If true, the current Request object will automatically determine the
      | language to use based on the value of the Accept-Language header.
      |
      | If false, no automatic detection will be performed.
      |
      */
      public $negotiateLocale = false;
  
      /*
      |--------------------------------------------------------------------------
      | Supported Locales
      |--------------------------------------------------------------------------
      |
      | If $negotiateLocale is true, this array lists the locales supported
      | by the application in descending order of priority. If no match is
      | found, the first locale will be used.
      |
      */
      public $supportedLocales = ['en'];
  
      /*
      |--------------------------------------------------------------------------
      | Application Timezone
      |--------------------------------------------------------------------------
      |
      | The default timezone that will be used in your application to display
      | dates with the date helper, and can be retrieved through app_timezone()
      |
      */
      public $appTimezone = 'America/New_York';
  
      /*
      |--------------------------------------------------------------------------
      | Default Character Set
      |--------------------------------------------------------------------------
      |
      | This determines which character set is used by default in various methods
      | that require a character set to be provided.
      |
      | See http://php.net/htmlspecialchars for a list of supported charsets.
      |
      */
      public $charset = 'UTF-8';
  
      /*
      |--------------------------------------------------------------------------
      | URI PROTOCOL
      |--------------------------------------------------------------------------
      |
      | If true, this will force every request made to this application to be
      | made via a secure connection (HTTPS). If the incoming request is not
      | secure, the user will be redirected to a secure version of the page
      | and the HTTP Strict Transport Security header will be set.
      */
      public $forceGlobalSecureRequests = false;
  
      /*
      |--------------------------------------------------------------------------
      | Session Variables
      |--------------------------------------------------------------------------
      |
      | 'sessionDriver'
      |
      |   The storage driver to use: files, database, redis, memcached
      |       - CodeIgniter\Session\Handlers\FileHandler
      |       - CodeIgniter\Session\Handlers\DatabaseHandler
      |       - CodeIgniter\Session\Handlers\MemcachedHandler
      |       - CodeIgniter\Session\Handlers\RedisHandler
      |
      | 'sessionCookieName'
      |
      |   The session cookie name, must contain only [0-9a-z_-] characters
      |
      | 'sessionExpiration'
      |
      |   The number of SECONDS you want the session to last.
      |   Setting to 0 (zero) means expire when the browser is closed.
      |
      | 'sessionSavePath'
      |
      |   The location to save sessions to, driver dependent.
      |
      |   For the 'files' driver, it's a path to a writable directory.
      |   WARNING: Only absolute paths are supported!
      |
      |   For the 'database' driver, it's a table name.
      |   Please read up the manual for the format with other session drivers.
      |
      |   IMPORTANT: You are REQUIRED to set a valid save path!
      |
      | 'sessionMatchIP'
      |
      |   Whether to match the user's IP address when reading the session data.
      |
      |   WARNING: If you're using the database driver, don't forget to update
      |            your session table's PRIMARY KEY when changing this setting.
      |
      | 'sessionTimeToUpdate'
      |
      |   How many seconds between CI regenerating the session ID.
      |
      | 'sessionRegenerateDestroy'
      |
      |   Whether to destroy session data associated with the old session ID
      |   when auto-regenerating the session ID. When set to FALSE, the data
      |   will be later deleted by the garbage collector.
      |
      | Other session cookie settings are shared with the rest of the application,
      | except for 'cookie_prefix' and 'cookie_httponly', which are ignored here.
      |
      */
      public $sessionDriver            = 'CodeIgniter\Session\Handlers\FileHandler';
      public $sessionCookieName        = 'ci_session';
      public $sessionExpiration        = 7200;
      public $sessionSavePath          = WRITEPATH . 'session';
      public $sessionMatchIP           = false;
      public $sessionTimeToUpdate      = 300;
      public $sessionRegenerateDestroy = false;
  
      /*
      |--------------------------------------------------------------------------
      | Cookie Related Variables
      |--------------------------------------------------------------------------
      |
      | 'cookiePrefix'   = Set a cookie name prefix if you need to avoid collisions
      | 'cookieDomain'   = Set to .your-domain.com for site-wide cookies
      | 'cookiePath'     = Typically will be a forward slash
      | 'cookieSecure'   = Cookie will only be set if a secure HTTPS connection exists.
      | 'cookieHTTPOnly' = Cookie will only be accessible via HTTP(S) (no javascript)
      |
      | Note: These settings (with the exception of 'cookie_prefix' and
      |       'cookie_httponly') will also affect sessions.
      |
      */
      public $cookiePrefix   = '';
      public $cookieDomain   = '';
      public $cookiePath     = '/';
      public $cookieSecure   = false;
      public $cookieHTTPOnly = false;
  
      /*
      |--------------------------------------------------------------------------
      | Reverse Proxy IPs
      |--------------------------------------------------------------------------
      |
      | If your server is behind a reverse proxy, you must whitelist the proxy
      | IP addresses from which CodeIgniter should trust headers such as
      | HTTP_X_FORWARDED_FOR and HTTP_CLIENT_IP in order to properly identify
      | the visitor's IP address.
      |
      | You can use both an array or a comma-separated list of proxy addresses,
      | as well as specifying whole subnets. Here are a few examples:
      |
      | Comma-separated:  '10.0.1.200,192.168.5.0/24'
      | Array:        array('10.0.1.200', '192.168.5.0/24')
      */
      public $proxyIPs = '';
  
      /*
      |--------------------------------------------------------------------------
      | Cross Site Request Forgery
      |--------------------------------------------------------------------------
      | Enables a CSRF cookie token to be set. When set to TRUE, token will be
      | checked on a submitted form. If you are accepting user data, it is strongly
      | recommended CSRF protection be enabled.
      |
      | CSRFTokenName   = The token name
      | CSRFCookieName  = The cookie name
      | CSRFExpire      = The number in seconds the token should expire.
      | CSRFRegenerate  = Regenerate token on every submission
      | CSRFRedirect    = Redirect to previous page with error on failure
      */
      public $CSRFTokenName  = 'csrf_test_name';
      public $CSRFCookieName = 'csrf_cookie_name';
      public $CSRFExpire     = 7200;
      public $CSRFRegenerate = true;
      public $CSRFRedirect   = true;
  
      /*
      |--------------------------------------------------------------------------
      | Content Security Policy
      |--------------------------------------------------------------------------
      | Enables the Response's Content Secure Policy to restrict the sources that
      | can be used for images, scripts, CSS files, audio, video, etc. If enabled,
      | the Response object will populate default values for the policy from the
      | ContentSecurityPolicy.php file. Controllers can always add to those
      | restrictions at run time.
      |
      | For a better understanding of CSP, see these documents:
      |   - http://www.html5rocks.com/en/tutorials/security/content-security-policy/
      |   - http://www.w3.org/TR/CSP/
      */
      public $CSPEnabled = false;
  
  }
  </code></pre>
  
  <p>when going to <a href="http://sub.domain.com" rel="nofollow noreferrer">http://sub.domain.com</a>, i am getting the default controller and view rendering.
  However the CSS assets and JS assets that are linked:
  <a href="https://sub.domain.com/assets/css/style.bundle.css" rel="nofollow noreferrer">https://sub.domain.com/assets/css/style.bundle.css</a></p>
  
  <p>are all going to a server error.
  the location of these files are actually in <a href="https://sub.domain.com/public/assets/css/style.bundle.css" rel="nofollow noreferrer">https://sub.domain.com/public/assets/css/style.bundle.css</a></p>
  
  <p>but I am trying to avoid using /public/ in the url.</p>
  
  <p>Any help or direction is appreciated.</p>
  
  <p>RD</p>