Hosting Iconify

This article explains how to host Iconify on your server, so your website does not rely on Iconify API servers.

Iconify API is available in 2 programming languages: PHP and Node.js

This tutorial explains both methods. For better performance use Node.js version.

Preparation

First you need to figure out where to host API.

If you are using PHP version, you can upload it to your existing website in sub-directory.

If you are using Node.js version, you should consider setting up reverse proxy.

Next step is to setup API and test it.

Custom API: PHP

Everything you need is available at Iconify GitHub repositories.

Server requirements

  • You need PHP 5.6 or newer version.
  • Script requires Apache web server with mod_rewrite enabled. It might be possible with other server software too if you can configure rewrite rules for it.
  • Files must be writable by same user that runs PHP scripts to allow writing to "cache" and "git-repos" directories.
  • If you are using function to synchronize repositories, make sure Git (version 2.x) is installed and is accessible from command line.
  • Do not install API in sub-directory of application that relies on mod_rewrite to avoid conflicts.

Clone or download Iconify API from GitHub: https://github.com/iconify-design/api.php

Then you need to install dependencies.

Installing dependencies

It is rather straightforward process if you are familiar with using Composer. If you are not familiar with Composer, it might be worth to learn it because almost all modern PHP frameworks use it, so you are very likely to encounter Composer again.

  1. Download and install Composer from getcomposer.org.
  2. Run composer install --no-dev to install all dependencies (see Composer documentation or ask on support forum if you are having troubles with this step).
  3. If you want to host custom icons, add your custom icons in directory "json". Make sure file name matches icons prefix (for icons with prefix "custom-icons" file should be named "custom-icons.json").

Then upload it all to your website.

After uploading files to your website you need to test it. Then you need to change Iconify configuration. See sections after Node.js instructions.

Custom API: Node.js

Node.js script is harder to setup, but it is preferred solution. It is slightly faster than PHP version because all collections are loaded only once.

Clone or download Iconify API from GitHub: https://github.com/iconify-design/api.js

Hosting with Elastic Beanstalk

If you are using Amazon Elastic Beanstalk, there is nothing to configure. API was tested with EB.

Compress directory, log in to AWS console, click "Elastic Beanstalk".

Select "Web development environment" option, then fill out form. From choice of platforms select "Node.js", in application code option upload API archive.

That's it. It will take few minutes to start. Your API instance will have custom sub-domain name assigned to it, use it to test API.

Hosting with custom hosting environment

Upload all files on server, SSH to server and install dependencies.

Installing dependencies

It is rather straightforward process if you are familiar with using NPM and Git.

  1. Run npm install --production to install all dependencies (see NPM documentation or ask on support forum if you are having troubles with this step).
  2. If you want to host custom icons, add your custom icons in directory "json". Make sure file name matches icons prefix (for icons with prefix "custom-icons" file should be named "custom-icons.json").

To run script in custom hosting environment you need to change configuration.

Port

By default script runs on port 3000. You might need to change it. There are 2 ways to change port:

  • Set environment variable "PORT"
  • Change "port" value in config.json
{
  "port": 3000
}

To start application you need to run node app or npm start that will run app.js

To make sure application runs without interruption, use pm2 or similar Node.js process manager to run application.

After starting application you need to test it to make sure it works and configure Iconify to use your API. See sections below.

HTTPS support

HTTPS support is a must for modern websites, but it is not handled by API script.

To use HTTPS you should setup Apache or NGINX reverse proxy or use CDN service such as CloudFlare.

You should consider setting up one or more of those systems anyway to handle things like rate limiting to avoid your Node.js application from getting hammered by bad clients.

For example, api.iconify.design uses Node.js version of API with NGINX reverse proxy and CloudFlare.

Testing

After uploading files on server (and starting process if you are using Node.js version) you need to test it to make sure API runs smoothly.

To test it you need to know URL where you have uploaded API and names of few icons you've added.

Lets assume you've uploaded files to http://my-website.com/api/

One of common icons that should exist is "mdi-home". Test API by checking if API can generate that icon.

To test SVG generator append icon name + ".svg" to URL:

http://my-website.com/api/mdi-home.svg

If visiting that URL shows you your custom icon, everything is working.

Then test icons list by adding collection name to URL + ".json?icons=" + names of few icons:

http://my-website.com/api/noto.json?icons=computer-disk,computer-mouse,control-knobs,couch-and-lamp,crayon

If everything is setup correctly, API should return JSON data for those icons.

PHP: error 404

If you are experiencing error 404 with PHP API, it is most likely caused by Apache configuration.

Make sure that:

  • mod_rewrite module is enabled
  • AllowOverride for directory where API is hosted is set to All
  • There are no .htaccess files in parent directories that could be causing conflicts. Do not install Iconify API in sub-directory of complex applications that use mod_rewrite such as WordPress or XenForo.

Configuring Iconify

After setting up your API you need to configure Iconify to use your API instead of api.iconify.design

To do that change configuration "API" right after including Iconify.

Code with API hosted on custom sub-domain:

<script src="//code.iconify.design/1/1.0.0-rc5/iconify.min.js"></script>
<script>
  Iconify.setConfig('API', '//api.my-website.com/{prefix}.js?icons={icons}');
</script>

Code with API hosted in sub-directory "/api/":

<script src="//code.iconify.design/1/1.0.0-rc5/iconify.min.js"></script>
<script>
  Iconify.setConfig('API', '//my-website.com/api/{prefix}.js?icons={icons}');
</script>

Building custom Iconify script

Another option is to clone Iconify script and change default API URL.

Click here to download or clone Iconify repository.

Change link to API in src/browser/with-api/defaults.js, then compile API by running node build/dist and you will find customized version of Iconify script in /dist/iconify.min.js

If you want to host everything yourself, there are also polyfills for old Internet Explorer that you might want to copy and change links in Iconify. See last few lines in src/browser/defaults.js

Then you can upload iconify.min.js to your server so you will be hosting everything yourself.

Configuring Iconify API for custom collection

If you want to use custom Iconify API only for collections with specific prefix, use setCustomAPI function:

Code with API hosted on custom sub-domain:

<script src="//code.iconify.design/1/1.0.0-rc5/iconify.min.js"></script>
<script>
  Iconify.setCustomAPI('custom-prefix', '//api.my-website.com/{prefix}.js?icons={icons}');
</script>

Code with API hosted in sub-directory "/api/":

<script src="//code.iconify.design/1/1.0.0-rc5/iconify.min.js"></script>
<script>
  Iconify.setCustomAPI('custom-prefix', '//my-website.com/api/{prefix}.js?icons={icons}');
</script>

Then Iconify will load all icons that start with "custom-prefix:" from your server.

This method can be used to host custom and premium icon sets.

Updating icon sets

At some point you might want to upload new icons set to API. How to do it without interrupting service?

Retrieving icons from Git repository

Both PHP and Node.js versions of Iconify API have ability to retrieve icons from Git repository.

There are two repositories in configuration:

  • iconify: this repository handles default Iconify icons set.
  • custom: this repository is for custom icons set.

This section of tutorial explains how to configure custom repository. However same method applies to iconify repository, except that you might not need to change Git link.

Read following tutorial to understand how to change configuration:

Configuring repository

First you need to get link to Git repository. Go to GitHub (or other Git service), find repository, click "clone or download" button and Git repository link.

GitHub offers two links: SSH and HTTPS. Which link to get?

  • If you are using private Git repository, use SSH link to repository and make sure server has all credentials to access it without requiring login/password.
  • If you are using public Git repository, use HTTPS link to repository.

Then put that link into configuration in sync.custom (or sync.iconify for Iconify repository)

{
  "sync": {
    "custom": "https://github.com/cyberalien/animated-icons.git",
    "custom-dir": "final"
  }
}

If JSON files are stored in sub-directory, also add "custom-dir" with location of JSON files relative to root directory. Do not include / at start or end. This applies only to custom repository, not to iconify repository.

Then you need to configure custom key. This is secret key that prevents other visitors from accessing synchronization function without permission. Set it to any string:

{
  "sync": {
    "secret": "secret-password-123"
  }
}

That is it. If you are using Node.js API, restart server. If you are using PHP API, purge cache by deleting PHP files from directory "cache".

How to synchronize repository

If your API is hosted at https://api.yourdomain.com/, open URL https://api.yourdomain.com/sync?repo=custom&key=secret-password-123 in browser.

You will not get any response indicating if synchronization worked or not. Node.js will respond with "ok" to any sync query, even incorrect ones. PHP will wait 15 seconds before returning empty page.

Why does synchronization behave that way? To prevent people from trying to guess secret key. With Node.js there will be instant response, synchronization will start asynchronously some time after response. PHP will wait for 15 seconds after receiving request before sending empty response.

Best way to check if synchronization worked is to wait until synchronization was supposedly completed and check one of new or changed icons.

If you are using Node.js API, you can also watch console if you have access to it. Node.js will start synchronization only 60 seconds after request. Why? To avoid multiple synchronization attempts if there were multiple requests within minute (for example if API synchronization is done by GitHub webhook and several commits are pushed within minute).

How to automate synchronization from GitHub

You can use GitHub webhooks to automatically synchronize repository when you push new commits.

To do that you need to have admin access to repository, so if you want to use synchronization with Iconify icons, you need to make your own fork of iconify-design/collections-json repository.

To add webhook go to repository, click "Settings" button, click "Webhooks" menu and "Add webhook" button.

In "payload URL" enter http://1.2.3.4/sync?repo=custom&key=secret-password-123

Keep other settings as default, click "Add webhook" button.

To test it you need to commit something to repository. Then open hooks list on GitHub, you will see status icon indicating if recent delivery was successful.

Automatically synchronizing repositories on startup

This function exists only in Node.js version of API. PHP does not have anything similar.

You can enable Node.js version to automatically pull latest versions of repositories from Git on startup.

This is very useful if you do not want to maintain API dependencies.

To enable it you need to change configuration option sync.sync-on-startup. There are 3 possible values:

  • never: default value. It means synchronization on startup is disabled.
  • missing: Only repositories that are missing will be synchronized.
  • always: All repositories will be synchronized.

This function will only work if repositories have been setup and secret key has been set.

Reloading dependencies

Another method of updating icon sets without stopping server is to reload dependencies.

Important: this method will not work if you are using synchronization function for same repository. Synchronized repository will override dependency.

PHP API

Update custom icons in directory "json".

To update default Iconify icons run composer update iconify/json

Then purge cache by removing php files from directory "cache".

Node.js API

First you need to enable reload function. To do that you need to set "reload-secret" configuration value to some custom string. It should be done before starting application.

{
  "reload-secret": "secret-password-123"
}

Update custom icons in directory "json".

To update default Iconify icons run npm update @iconify/json

Then open reload URL in your browser. If your API is hosted at https://api.yourdomain.com/, open URL https://api.yourdomain.com/reload?key=secret-password-123 in browser.