# DeviceAtlas NGINX Plus Module FreeBSD Installation # Provides detailed instructions to install and use the DeviceAtlas NGINX Plus module. 1. Installing DeviceAtlas NGINX Plus module on FreeBSD 2. NGINX setup with DeviceAtlas 3. DeviceAtlas data file reload 4. Example configurations 5. Debugging 6. Common errors ### Installing DeviceAtlas NGINX Plus module on FreeBSD ### To use the module, you will need to download and install DeviceAtlas NGINX Plus module. Download [FreeBSD NGINX Plus DeviceAtlas module](https://deviceatlas.com/resources/download-enterprise-api) depending on your NGINX Plus version and server architecture. To install the DeviceAtlas NGINX Plus module on FreeBSD please run following command. ```sh pkg install nginx-plus-module-deviceatlas-freebsd-<version>.txz ``` Installing module will ask user to edit `/usr/local/etc/deviceatlas/json-downloads.conf` file to provide DeviceAtlas licence key and location for DeviceAtlas to store the data file. Followed by editing `/etc/crontab` file to schedule for automated data file downloads. ### NGINX setup with DeviceAtlas ### To use the module, you will need to download the required data file, save it locally and set the `devatlas_db` path in `nginx.conf`. To get the data file for device detection, please see the [Device Data](https://deviceatlas.com/resources/getting-the-data/device-data) documentation. ** A snippet from nginx.conf ** ```sh # Uncomment next line and fix the path if using dynamic or NGINX Plus module. #load_module /usr/local/libexec/nginx/ngx_http_deviceatlas_module.so; http { variables_hash_max_size 4096; ## DeviceAtlas Detection devatlas_db /usr/local/var/lib/deviceatlas/DeviceAtlas.json; ## DeviceAtlas variables prefix (optional) # All DeviceAtlas properties are prefixed with da_ and are available # as NGINX's environment variables (all dots are replaced with underscores). # Uncomment `devatlas_property_prefix` line to set a custom prefix for # the DeviceAtlas variables (default is da_). #devatlas_property_prefix http_; ## Property filter (optional) # By default the DeviceAtlas module registers all available properties # from the JSON file. If at least one `devatlas_property` definition is # found the module will register only those properties which are defined. # For a list of all properties see https://deviceatlas.com/properties devatlas_property primaryHardwareType; devatlas_property osName; devatlas_property osVersion; devatlas_property browserName; devatlas_property browserVersion; ## Client-side Component (optional) # To use the Client-side Component with the NGINX module, the JavaScript # file located in ExtraTools/ClientSide/ must be included on every webpage. # The JS library will create a cookie with the client properties. The # NGINX module reads this cookie and merges the properties with the server # side detected properties. devatlas_properties_cookie DAPROPS; server { listen 8080; server_name localhost; location / { fastcgi_param REQUEST_METHOD $request_method; fastcgi_param QUERY_STRING $query_string; # DeviceAtlas properties # nginx environment variables are formed as follow # <prefix><property name> e.g. da_model fastcgi_param DA_PRIMARY_HARDWARE_TYPE $da_primaryHardwareType; fastcgi_param DA_OS_NAME $da_osName; fastcgi_param DA_OS_VERSION $da_osVersion; fastcgi_param DA_BROWSER_NAME $da_browserName; fastcgi_param DA_BROWSER_VERSION $da_browserVersion; # More NGINX properties here } } } ``` ### DeviceAtlas data file reload ### The DeviceAtlas data file can be reloaded in place without restarting NGINX. Replace the on-disk file with a new data file downloaded from deviceatlas.com and trigger an NGINX reload. NGINX will continue to serve requests while the new data file is being loaded. An NGINX reload can be triggered by calling `nginx reload` or `service nginx reload`. The reload will ignore corrupt or missing data files and continue using the previous in-memory version. The NGINX error log will contain an error message if this occurs. ### Example configurations ### There are multiple NGINX configuration files and snippets for common use-cases available at `/usr/local/share/deviceatlas/examples` - Hello World - Non-human traffic detection - Non-human traffic detection (with LUA) - Image optimisation - Mobile redirection - Language redirection - Passing variables downstream as headers #### Common settings (for all examples) #### All examples below requires following configuration. ** In main block (i.e. outside of `HTTP` and `server` blocks): ** ``` # Load DeviceAtlas module (Dynamic or NGINX Plus module option only) load_module /usr/local/libexec/nginx/ngx_http_deviceatlas_module.so; ``` ** In HTTP block: ** ``` variables_hash_max_size 4096; devatlas_db /usr/local/var/lib/deviceatlas/DeviceAtlas.json; ``` #### EXAMPLE 1 - Hello World #### This is a very simple configuration to ensure that DeviceAtlas is working (like Hello World, for the module). The path `/DeviceAtlasTest` will return a plain text response containing the device type e.g. "Mobile Phone" or "Tablet". ** In HTTP block: ** ``` # Assign DeviceAtlas properties as maps. # (It's recommended to always use default values as follows.) map $da_primaryHardwareType $primaryHardwareType { default $da_primaryHardwareType; "" "No primary hardware type available"; } ``` ** In server block: ** ``` location /DeviceAtlasTest { add_header Content-Type text/plain; return 200 $primaryHardwareType; } ``` #### EXAMPLE 2 - Non-human traffic detection #### This configuration shows how you might treat traffic for known bots. In this case they are redirected to a separate page but alternate content could be served also. ** In server block: ** ``` location / { default_type 'text/plain'; content_by_lua_block { /* General property to detect all types of bots traffic */ local isNonHumanTraffic = ( ngx.var.da_isRobot == "1" ) if isNonHumanTraffic then ngx.say("You are a bot !!") else /* Creation of an environement variable to store the hardware type */ local primaryHardwareType = 'generic' if ngx.var.da_primaryHardwareType then primaryHardwareType = ngx.var.da_primaryHardwareType end set_by_lua $primary_hardware_type primaryHardwareType end } } ``` #### EXAMPLE 3 - Non-human traffic detection (with LUA) #### This configuration shows how you might treat traffic for known bots. In this case they are redirected to a separate page but alternate content could be served also. ** In HTTP block: ** ``` # Assign DeviceAtlas properties as maps. # (It's recommended to always use default values as follows.) map $da_isRobot $robot { true 1; false 0; default 0; } ``` ** In server block: ** ``` # Redirect robots to scraping policy page if ($robot) { rewrite ^ http://www.example.com/scrapingpolicy.html; } ``` #### EXAMPLE 4 - Image optimisation - part #1 #### This example demonstrates how you might resize images to maximum display size for a given device. Desktop devices will see no change, mobile devices should be served images appropriate to their resolutions. Resized images are cached to ensure minimal load on server (one resize operation per target resolution). This is part #1, see part #2 for an actual resizer listening at port 9000. ** In HTTP block: ** ``` # Assign DeviceAtlas properties as maps. # (It's recommended to always use default values as follows.) map $da_usableDisplayWidth $displayWidth { default $da_usableDisplayWidth; "" "-"; } map $da_usableDisplayHeight $displayHeight { default $da_usableDisplayHeight; "" "-"; } ``` ** In server block: ** ``` location ~* "^/images/(.*)" { set $image_path $1; proxy_pass http://127.0.0.1:9000/image_resizer/$image_path?width=$displayWidth&height=$displayHeight; proxy_cache resized; proxy_cache_valid 180m; } ``` #### Image optimisation - part #2 #### ** In HTTP block: ** ``` limit_req_zone "1" zone=2persec:32k rate=2r/s; ``` ** In server block: ** ``` listen 9000; allow 127.0.0.1; deny all; limit_req zone=2persec burst=10; location /image_resizer { alias /usr/share/nginx/html/path/to/images; image_filter resize $arg_width $arg_height; } ``` #### EXAMPLE 5 - Mobile redirection #### This example demonstrates how you might rewrite URLS to serve mobile-specific content (e.g. AMP pages) to certain device classes. ** In HTTP block: ** ``` # Assign DeviceAtlas properties as maps. # (It's recommended to always use default values as follows.) map $da_mobileDevice $mobile { true 1; false 0; default 0; } ``` ** In server block: ** ``` # Send mobile device to AMP version of content if ($mobile) { rewrite ^(.*)$ /AMP/$1 break; } ``` #### EXAMPLE 6 - Language redirection #### This example demonstrates how you might rewrite URLS based on a client's detected language. ** In HTTP block: ** ``` # Assign DeviceAtlas properties as maps. # (It's recommended to always use default values as follows.) map $da_language $language { default $da_language; "" "en"; } ``` ** In server block: ** ``` location / { rewrite ^(.*)$ /$language/$1; } ``` #### EXAMPLE 7 - Passing variables downstream as headers #### This example demonstrates how you might pass variables downstream via request headers. ** In server block (LB): ** ``` location /DeviceAtlasTest { proxy_set_header X-DeviceAtlas-isMobilePhone $da_isMobilePhone; proxy_pass http://localhost:8080; } ``` ** In HTTP block (downstream): ** In case of underscore headers, set by LB, an extra directive is needed to be set on the downstream servers. e.g. proxy_set_header DA_IS_MOBILE_PHONE $da_isMobilePhone; This is not needed if the header names are set with dashes as `X-DeviceAtlas-<variable>` (as is in the example above). ``` underscores_in_headers on; ``` ### Debugging ### ** Is DeviceAtlas module running? ** The simplest way to confirm if the DeviceAtlas module is loaded successfully is by looking in NGINX's error log (typically in `/var/log/nginx-error.log`). It will have "[notice]" lines similar to the following in it: ``` [notice] DeviceAtlas cookie name 'DAPROPS' in /usr/local/etc/nginx/nginx.conf:57 [notice] DeviceAtlas, environment variable 'da_primaryHardwareType' added (property 'primaryHardwareType') in /usr/local/etc/nginx/nginx.conf:57 [notice] DeviceAtlas, environment variable 'da_osName' added (property 'osName') in /usr/local/etc/nginx/nginx.conf:57 [notice] DeviceAtlas, environment variable 'da_osVersion' added (property 'osVersion') in /usr/local/etc/nginx/nginx.conf:57 ``` ** Checking DeviceAtlas values ** The easiest way to debug issues is to add the DeviceAtlas properties to the NGINX log file so that you can see their value for each request. ``` log_format main '$remote_addr - $remote_user [$time_local] "$request" ' '$status $body_bytes_sent "$http_referer" ' '"$http_user_agent" "$http_x_forwarded_for" ' '"$da_mobileDevice" "$da_vendor $da_model"'; ``` ### Common errors ### ** Version compatibility ** To prevent the error below ensure that appropriate DeviceAtlas module is used for NGINX Plus version. For NGINX Plus r14 1.13.7 use nginx-plus-module-deviceatlas-<os>-<arch>-1.13.7.txz For NGINX Plus r13 1.13.4 use nginx-plus-module-deviceatlas-<os>-<arch>-1.13.4.txz ```sh nginx: [emerg] module "/usr/local/libexec/nginx/ngx_http_deviceatlas_module.so" version 1013004 instead of 1013007 ``` - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - _ Copyright (c) DeviceAtlas Limited 2021. All Rights Reserved. _ https://deviceatlas.com <!-- HTML+JS for document formatting when opened in browser --> <div class="btn-group" id="main-menu" style="float:right"><a class="btn dropdown-toggle" data-toggle="dropdown" href="#">Menu<span class="caret"></span></a><ul class="dropdown-menu"><li><a href="README.html">Main</a></li><li class="disabled"><a href="README.N.html">NGINX Plus Module FreeBSD Installation</a></li></ul></div>