/impress

Impress Application Server for node.js. All decisions are made. Solutions are scaled. Tools are provided and optimized for high load. Ready for applied development and production.

Primary LanguageJavaScript

impress logo

Build Status Dependency Status Codacy Badge Inline docs

Impress Application Server for node.js. All decisions are made. Solutions are scaled. Tools are provided and optimized for high load. Ready for applied development and production.

Impress (Impress Application Server, IAS) follows alternative way in several aspects:

  • No callback chain (no middleware), hierarchically inheritable hash routing instead
  • Monolithic high coupling core with obligatory things optimized for performance
  • Extensible plug-ins format for optionally needed things
  • Applied code simplicity, API code high-level abstraction and brevity
  • Support for both Stateful and Stateless approach
  • Application can't include Application Server, quite the opposite, Application Server is a container for Applications
  • No I/O is faster even then async I/O, so maximum memory usage and lazy I/O is the choice

Features

  • Can serve multiple applications and sites on multiple domains
  • Serves multiple ports, network interfaces, hosts and protocols
  • Can scale on multiple servers
  • Supports application sandboxing (configuration, db and memory access isolation)
  • Supports one or multiple CPU cores with following instantiation strategies:
    • Single instance (one process)
    • Instance specialization (multiple processes, one master and different workers for each server)
    • Multiple instances (multiple processes, one master and identical workers with no sticky)
    • IP sticky (multiple processes, one master and workers with serving sticky by IP)
  • URL routing based on file system
    • No need to write routing manually in code, just create folder if new AJAX API method needed
    • File system watching for cache reloading when file changes on disk
    • Caching server-side executable JavaScript in memory
  • Handlers inheritance override hierarchically uning filesystem
  • Middleware emulation (adding URL routing to handler-functions programmatically)
  • API development support (simple way for JSON-based WEB-services development)
    • RPC-style API (Stateful, state stored in memory between requests)
    • REST-style API (Stateless, each call is separate, no state in memory)
    • Impress RPC (long live and full duplex RPC via websocket)
  • Multiple handlers (all handlers are optional and inheritable/overridable):
    • access.js - returns access modifiers
    • request.js - executing for all requests (any HTTP verbs and before verb handler)
    • HTTP verbs: get.js, post.js, etc. - executes for certain HTTP verb
    • end.js - executes after HTTP verb handler for all verbs
    • lazy.js - lazy handler executes after the request has already returned to the client-side
    • error.js - executed only if an error occurred while processing the request or in any previous handler
  • Supported multiple AJAX API result types:
    • JSON for most APIs (including safe serialization)
    • JSONP (for cross-domain requests)
    • CSV (JavaScript Object Notation)
    • HTML (aor any extension unknown for IAS) - for AJAX server-side HTML rendering
  • Server server-side simple templating
    • Caching templates in memory and ready (rendered) pages optional caching
    • Supports array and hash iterations and sub-templates including
    • Template personalization for user groups
  • Application config changes with zero downtime
    • Flexible configuration in JS or JSON format
    • File watch and automatic soft reloading when configuration js file changes
    • No Impress server hard restarting
  • Serving static files with in-memory preprocessing
    • Gzipping and HTTP request field "if-modified-since" field support and HTTP 304 "Not Modified" answer
    • Memory caching and file system watching for cache reloading when files changed on disk
    • JavaScript optional (configurable) minification, based on module "uglify-js" as Impress plug-in
    • SASS Syntactically Awesome Stylesheets compiling .scss to .css in memory cache
  • Built-in sessions support with authentication and user groups and anonymous sessions
    • Sessions and cookies (memory state or persistent sessions with MongoDB)
    • Access modifiers for each folder in access.js files and access inheritance
  • Multiple protocols support:
    • HTTP and HTTPS (node native libraries)
    • Implemented SSE (Server-Sent Events) with channels and multi-cast
    • WebSockets support (even on shared host/port with other handlers, using regular connection upgrade)
    • TCP and UDP sockets support
  • Reverse-proxy (routing request to external HTTP server with URL-rewriting)
  • Logging: "access", "debug", "error" and "slow" logs
    • Log rotation: keep logs N days (configurable) delete files after N days
    • Log buffering, write stream flushing interval
    • Each application can be logged to own folder and/or to server-wide logs
  • Connection drivers for database engines:
    • MySQL data access layer based on felixge/mysql low-level drivers (separate module "musql-utilities")
      • MySQL Data Access Methods: queryRow, queryValue, queryCol, queryHash, queryKeyValue
      • MySQL Introspection Methods: primary, foreign, constraints, fields, databases, tables, databaseTables, tableInfo, indexes, processes, globalVariables, globalStatus, users
      • MySQL SQL Autogenerating Methods: select, insert, update, upsert, count, delete
      • Events: 'query', 'slow'
    • MongoDB drivers as Impress plug-in
    • PgSQL drivers as Impress plug-in
    • Memcached drivers as Impress plug-in
    • Relational schema generator from JSON database schemas
  • Sending Emails functionality using "nodemailer" module as Impress plug-in
  • File utilities: upload, download, streaming
  • Integrated DBMI (Web-based management interface for MySQL and MongoDB)
  • GeoIP support, based on "geoip-lite" module as Impress plug-in (uses MaxMind database)
  • Social networking login using Passport.js as plug-in
  • Built-in simple testing framework
  • Server health monitoring
  • Built-in data structures validation and preprocessing library
  • Process forking:
    • Long workers with "client" object forwarding to separate process
    • Task scheduling (interval or certain time)
  • Cross-process communication
    • IPC support (interprocess communications) for event delivery between Node.js instances
    • ZMQ support (Zero MQ) ar an alternative event delivery transport
    • State synchronization mechanism with transactions and subscription
  • Implemented V8 features support:
    • Long stack trace with --stack-trace-limit=1000 and stack output minification
    • Wrapper for V8 internal functions with --allow-natives-syntax
    • Manual garbage collection with --nouse-idle-notification --expose-gc
  • HTTP base authentication implemented (optional omitting local requests)

Examples

Example #1
To create GET request handler for URL /api/method.json
File /api/method.json/get.js

module.exports = function(client, callback) {
  callback({ field: 'value' });
}

Result: { "field": "value" }

Example #2
To create POST request handler for URL /api/method.json
File /api/method.json/post.js

module.exports = function(client, callback) {
  dbImpress.users.find({ group: client.fields.group }).toArray(function(err, nodes) {
    callback(nodes);
  });
}

Result:

[
  { "login": "Vasia Pupkin", "password": "whoami", "group": "users" },
  { "login": "Marcus Aurelius", "password": "tomyself", "group": "users" }
]

Example #3
File "access.js" works similar to ".htaccess" and allow one to define access rules for each folder, by simply putting "access.js" in it.
If folder does not contain "access.js" it inherits access rules from its parent folder, all the way up to the project root.

Example:

module.exports = {
  guests:  true,  // Allow requests from anonimous users (not logged or no session)
  logged:  true,  // Allow requests from logged users
  http:    true,  // Allow requests using http protocol
  https:   true,  // Allow requests using https protocol
  groups:  [],    // Allow access for user groups listed in array
                  //   or for all if array is empty or no groups field specified
  intro:   true,  // Generate introspection for API methods in this directory
  index:   false, // Generate directory index
  virtual: true   // Allow requests to virtual paths, for CMS and REST URLs, etc.
}

Installation and upgrade

  • Install to the current folder: npm install impress
  • Install using package.json, add to dependencies and run npm install
  • Installation scripts for an empty server (from the scratch)
    • For CentOS 6 /deploy/centos6x32.sh and centos6x64.sh (tested on CentOS 6.6 32/64bit minimal)
    • For CentOS 7 /deploy/centos7x64.sh (tested on CentOS 7.0 with systemd 64bit minimal)
    • For Ubuntu 14 /deploy/ubuntu.sh (tested on Ubuntu 14.04 64bit minimal)
    • For Debian 7 /deploy/debian.sh (tested for Debian 7.5 64bit minimal)

You can prepare scripts based on examples above and run at a target server shell: curl http://host/path/install.sh | sh or wget http://host/path/install.sh -O - | sh

If Impress Application Server is already installed in directory you want to install/update it using npm, /applications directory contains applications and /config contains configuration, Impress will safely detect previous installation and update libraries and dependencies.

Impress CLI commands

You can use following commands from any directory:

  • impress path <path> to display or change path to IAS
  • impress start to start IAS server
  • impress stop to stop IAS server
  • impress restart to restart IAS server
  • impress status to display IAS status
  • impress update to update IAS version
  • impress autostart [on|off] to add/remove IAS to autostart on system reboot
  • impress list to see IAS applications list
  • impress add [path] to add application
  • impress remove [name] to remove application
  • impress new [name] to create application

Configuration

  1. Install Impress as described above.
  2. Edit /config/*.js to configure Application Server (set IP address in servers.js)
  3. After installation you have example application in directory /applications, you can rename it and/or place there other applications
  4. Edit /applications/example/config/hosts.js, change 127.0.0.1 to myapp.com, certainly you need to register and configure domain name myapp.com or just add it into hosts file in your OS
  5. Place your html to /applications/example/app/html.template and copy required files into directories /static/js, /static/css, /static/images and start application API development
  6. Run Impress using command service impress start or systemctl start impress (if installed as a service) or node server.js

Contributors

License

Dual licensed under the MIT or RUMI licenses.

Copyright (c) 2012-2015 MetaSystems <timur.shemsedinov@gmail.com>

RUMI License: Everything that you want, you are already that.
// Jalal ad-Din Muhammad Rumi