skip to Main Content

We’re using Apache 2.4 with React 17 and a Django 3.2 (Python 3.9) application. Curious about a better way to set up our Apache configs to route requests to the React and Django apps. Right now, our Apache virtual hosts file hard-codes which routes need to be handled by the React app vs which need to be handled by Django …

    AliasMatch ^/(?!people)(?!states/)(?!countries/)(?!predefined_types/)(?!coop_types/)(?!coops/)(?!data)(?!save_to_sheet_from_form).* /var/www/html/client/build/$0

    <Directory "/var/www/html/client/build/">
      Options Indexes FollowSymLinks
      AllowOverride all
    </Directory>

    WSGIDaemonProcess ssl_directory home=/var/www/html/web python-home=/var/www/html/web/venv
    WSGIProcessGroup ssl_directory
    WSGIScriptAlias /coops /var/www/html/web/directory/wsgi.py/coops process-group=ssl_directory
    WSGIScriptAlias /data /var/www/html/web/directory/wsgi.py/data process-group=ssl_directory
    WSGIScriptAlias /countries /var/www/html/web/directory/wsgi.py/countries process-group=ssl_directory
    WSGIScriptAlias /states /var/www/html/web/directory/wsgi.py/states process-group=ssl_directory
    WSGIScriptAlias /predefined_types /var/www/html/web/directory/wsgi.py/predefined_types process-group=ssl_directory
    WSGIScriptAlias /coop_types /var/www/html/web/directory/wsgi.py/coop_types process-group=ssl_directory
    WSGIScriptAlias /people /var/www/html/web/directory/wsgi.py/people process-group=ssl_directory
    WSGIScriptAlias /save_to_sheet_from_form /var/www/html/web/directory/wsgi.py/save_to_sheet_from_form process-group=ssl_directory

The Django app, for its part, defines urls in the standard way (in our urls.py file) …

...
urlpatterns = [
    path('data', views.data, name='data'),
    path('coops/no_coords', views.coops_wo_coordinates, name='coops_wo_coordinates'),
    path('coops/unapproved', views.unapproved_coops, name='unapproved_coops'),
    path('coops/', views.CoopList.as_view()),
    path('coops/<int:pk>/', views.CoopDetail.as_view()),
    path('people/', views.PersonList.as_view()),
    path('people/<int:pk>/', views.PersonDetail.as_view()),
    path('users/', views.CreateUserView.as_view()),
    path('predefined_types/', views.CoopTypeList.as_view()),
    path('coop_types/', views.CoopTypeList.as_view()),
    path('countries/', views.CountryList.as_view()),
    path('states/<country_code>', views.StateList.as_view()),
    path('login', views.signin),
    path(settings.LOGOUT_PATH, views.signout),
    path('user_info', views.user_info),
]

urlpatterns = format_suffix_patterns(urlpatterns)

Is there a more automated way we can get Apache to know what routes shoudl go to Django vs React? Whenever we add a new Django endpoint, we have to add a hard-coded exception in our Apache configs.

Edit: Here is an example how I make a React call to the API …

const { REACT_APP_PROXY } = process.env;

class PersonService {
  getById(id, callback) {
    fetch(REACT_APP_PROXY + "/people/" + id)
      .then((response) => {
        return response.json();
      })
      .then((data) => {
        const person = data;
        person.contact_methods.map((contact_method) => {
          if (contact_method.type == "PHONE") {
            person.phone = contact_method.phone.substring(2);
          } else if (contact_method.type == "EMAIL") {
            person.email = contact_method.email;
          }
        });
        if (callback) callback(person);
      });
  }
}

2

Answers


  1. Concerning python there are two wsgi-options that could help you to reduce the required lines and steps.

    1. Using the WSGIScriptAlias directive to map to a directory containing
      any number of WSGI applications:

      WSGIScriptAlias /wsgi/ /usr/local/wsgi/scripts/
      

      When this is used, the next part of the URL after the URL prefix is
      used to identify which WSGI application script file within the target
      directory should be used. Both the mount point and the directory path
      must have a trailing slash.

    2. Another option is intended primarily to suppress the extension in the
      Frontend but could be used too to redirect based on different aspects:

      WSGIScriptAliasMatch ^/wsgi/([^/]+) /usr/local/wsgi/scripts/$1.wsgi
      

      In this case, any path information appearing after the URL prefix, will be mapped to a corresponding WSGI script file in the directory, but with a ‘.wsgi’ extension. The extension would though not need to be included in the URL.

    The options can be configured with common Apache directives too, and there are additional features like directory index can be configured like that, it’s useful to read this page about all the options: https://modwsgi.readthedocs.io/en/master/user-guides/configuration-guidelines.html

    Furthermore you’ve the option to use the powerful mod_rewrite. Certainly there are many more options, most important is that to distinguish between script-types you’ve to have some aspect in the url or path to decide where to redirect. It can be a suffix and / or usage of WSGIScriptAlias which both would be most simple but could be based on mod_mime perhaps too.

    So actually the question in return is how far you’re willing to use suffixes or URLs that make a distinction possible and easy enough to be handled by the offered options.

    One aspect to consider is that a python app can reference js-files too, so simply a suffix might not be enough but if full paths are provided that’s perhaps not too difficult to handle.

    Login or Signup to reply.
  2. With mod_rewrite you have full control over redirection and remapping in Apache

    Redirecting and Remapping with mod_rewrite

    You should implement something like this:

    RedirectMatch "^/docs/(.*)" "http://new.example.com/docs/$1"
    

    or

    RewriteRule ^images/([^/]+)$ /assets/images/public/$1 [L]
    

    That redirects each part of application documents to its corresponding handler.

    RedirectMatch "^/react-docs/(.*)" "http://react-handler.example.com/react-docs/$1"
    

    As you see you need something in your URL that RedirectMatch or RewriteRule uses Regex on it for separating and sending each document to corresponding handler.

    Q&As on mod_rewrite

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search