diff --git a/README.md b/README.md
index e32f026..26d015b 100644
--- a/README.md
+++ b/README.md
@@ -135,9 +135,11 @@ Emits `message` when a message arrives.
| [options.polling.autoStart] | Boolean
| true
| Start polling immediately |
| [options.webHook] | Boolean
| Object
| false
| Set true to enable WebHook or set options |
| [options.webHook.port] | Number
| 8443
| Port to bind to |
-| [options.webHook.key] | String
| | Path to file with PEM private key for webHook server. (Read synchronously!) |
-| [options.webHook.cert] | String
| | Path to file with PEM certificate (public) for webHook server. (Read synchronously!) |
+| [options.webHook.key] | String
| | Path to file with PEM private key for webHook server. The file is read **synchronously**! |
+| [options.webHook.cert] | String
| | Path to file with PEM certificate (public) for webHook server. The file is read **synchronously**! |
+| [options.webHook.pfx] | String
| | Path to file with PFX private key and certificate chain for webHook server. The file is read **synchronously**! |
| [options.webHook.autoOpen] | Boolean
| true
| Open webHook immediately |
+| [options.webHook.https] | Object
| | Options to be passed to `https.createServer()`. Note that `options.webHook.key`, `options.webHook.cert` and `options.webHook.pfx`, if provided, will be used to override `key`, `cert` and `pfx` in this object, respectively. See https://nodejs.org/api/https.html#https_https_createserver_options_requestlistener for more information. |
| [options.onlyFirstMatch] | Boolean
| false
| Set to true to stop after first match. Otherwise, all regexps are executed |
| [options.request] | Object
| | Options which will be added for all requests to telegram api. See https://github.com/request/request#requestoptions-callback for more information. |
| [options.baseApiUrl] | String
| https://api.telegram.org
| API Base URl; useful for proxying and testing |
diff --git a/src/telegram.js b/src/telegram.js
index 9f7674d..6476251 100644
--- a/src/telegram.js
+++ b/src/telegram.js
@@ -47,9 +47,17 @@ class TelegramBot extends EventEmitter {
* @param {Boolean} [options.polling.autoStart=true] Start polling immediately
* @param {Boolean|Object} [options.webHook=false] Set true to enable WebHook or set options
* @param {Number} [options.webHook.port=8443] Port to bind to
- * @param {String} [options.webHook.key] Path to file with PEM private key for webHook server. (Read synchronously!)
- * @param {String} [options.webHook.cert] Path to file with PEM certificate (public) for webHook server. (Read synchronously!)
+ * @param {String} [options.webHook.key] Path to file with PEM private key for webHook server.
+ * The file is read **synchronously**!
+ * @param {String} [options.webHook.cert] Path to file with PEM certificate (public) for webHook server.
+ * The file is read **synchronously**!
+ * @param {String} [options.webHook.pfx] Path to file with PFX private key and certificate chain for webHook server.
+ * The file is read **synchronously**!
* @param {Boolean} [options.webHook.autoOpen=true] Open webHook immediately
+ * @param {Object} [options.webHook.https] Options to be passed to `https.createServer()`.
+ * Note that `options.webHook.key`, `options.webHook.cert` and `options.webHook.pfx`, if provided, will be
+ * used to override `key`, `cert` and `pfx` in this object, respectively.
+ * See https://nodejs.org/api/https.html#https_https_createserver_options_requestlistener for more information.
* @param {Boolean} [options.onlyFirstMatch=false] Set to true to stop after first match. Otherwise, all regexps are executed
* @param {Object} [options.request] Options which will be added for all requests to telegram api.
* See https://github.com/request/request#requestoptions-callback for more information.
diff --git a/src/telegramWebHook.js b/src/telegramWebHook.js
index 710c77f..05bd1c2 100644
--- a/src/telegramWebHook.js
+++ b/src/telegramWebHook.js
@@ -24,19 +24,25 @@ class TelegramBotWebHook {
this.token = token;
this.options = options;
this.options.port = options.port || 8443;
+ this.options.https = options.https || {};
this.callback = callback;
this._regex = new RegExp(this.token);
this._webServer = null;
this._requestListener = this._requestListener.bind(this);
this._parseBody = this._parseBody.bind(this);
- if (options.key && options.cert) { // HTTPS Server
- debug('HTTPS WebHook enabled');
- const opts = {
- key: fs.readFileSync(options.key),
- cert: fs.readFileSync(options.cert)
- };
- this._webServer = https.createServer(opts, this._requestListener);
+ if (options.key && options.cert) {
+ debug('HTTPS WebHook enabled (by key/cert)');
+ this.options.https.key = fs.readFileSync(options.key);
+ this.options.https.cert = fs.readFileSync(options.cert);
+ this._webServer = https.createServer(this.options.https, this._requestListener);
+ } else if (options.pfx) {
+ debug('HTTPS WebHook enabled (by pfx)');
+ this.options.https.pfx = fs.readFileSync(options.pfx);
+ this._webServer = https.createServer(this.options.https, this._requestListener);
+ } else if (options.https) {
+ debug('HTTPS WebHook enabled by (https)');
+ this._webServer = https.createServer(this.options.https, this._requestListener);
} else {
debug('HTTP WebHook enabled');
this._webServer = http.createServer(this._requestListener);
diff --git a/test/telegram.js b/test/telegram.js
index 3364448..a2b18b4 100644
--- a/test/telegram.js
+++ b/test/telegram.js
@@ -1,4 +1,4 @@
-const Telegram = require('../lib/telegram');
+const TelegramBot = require('../lib/telegram');
const Promise = require('bluebird');
const request = require('request-promise');
const assert = require('assert');
@@ -8,7 +8,9 @@ const path = require('path');
const is = require('is');
const utils = require('./utils');
+// Allows self-signed certificates to be used in our tests
process.env.NODE_TLS_REJECT_UNAUTHORIZED = '0';
+
const TOKEN = process.env.TEST_TELEGRAM_TOKEN;
if (!TOKEN) {
throw new Error('Bot token not provided');
@@ -19,12 +21,15 @@ const USERID = process.env.TEST_USER_ID || 777000;
const GROUPID = process.env.TEST_GROUP_ID || -1001075450562;
const GAME_SHORT_NAME = process.env.TEST_GAME_SHORT_NAME || 'medusalab_test';
const timeout = 60 * 1000;
-const staticPort = 8091;
-const pollingPort = 8092;
-const webHookPort = 8093;
-const pollingPort2 = 8094;
-const webHookPort2 = 8095;
+let portindex = 8091;
+const staticPort = portindex++;
+const pollingPort = portindex++;
+const webHookPort = portindex++;
+const pollingPort2 = portindex++;
+const webHookPort2 = portindex++;
const staticUrl = `http://127.0.0.1:${staticPort}`;
+const key = `${__dirname}/../examples/key.pem`;
+const cert = `${__dirname}/../examples/crt.pem`;
let FILE_ID;
let GAME_CHAT_ID;
let GAME_MSG_ID;
@@ -37,7 +42,7 @@ before(function beforeAll() {
});
});
-describe('Telegram', function telegramSuite() {
+describe('TelegramBot', function telegramSuite() {
let bot;
let testbot;
let botPolling;
@@ -45,8 +50,8 @@ describe('Telegram', function telegramSuite() {
before(function beforeAll() {
this.timeout(timeout);
- bot = new Telegram(TOKEN);
- testbot = new Telegram(TOKEN, {
+ bot = new TelegramBot(TOKEN);
+ testbot = new TelegramBot(TOKEN, {
baseApiUrl: `http://127.0.0.1:${pollingPort}`,
polling: {
autoStart: false,
@@ -56,11 +61,11 @@ describe('Telegram', function telegramSuite() {
port: webHookPort,
},
});
- botPolling = new Telegram(TOKEN, {
+ botPolling = new TelegramBot(TOKEN, {
baseApiUrl: `http://127.0.0.1:${pollingPort2}`,
polling: true,
});
- botWebHook = new Telegram(TOKEN, {
+ botWebHook = new TelegramBot(TOKEN, {
webHook: {
port: webHookPort2,
},
@@ -136,6 +141,31 @@ describe('Telegram', function telegramSuite() {
});
});
+ describe('WebHook HTTPS', function webHookHTTPSSuite() {
+ const port = portindex++;
+ let httpsbot;
+ afterEach(function afterEach() {
+ return httpsbot.closeWebHook();
+ });
+ it('is enabled, through options.key and options.cert', function test() {
+ httpsbot = new TelegramBot(TOKEN, { webHook: { port, key, cert } });
+ return utils.sendWebHookMessage(port, TOKEN, { https: true });
+ });
+ it('is enabled, through options.pfx');
+ it('is enabled, through options.https', function test() {
+ httpsbot = new TelegramBot(TOKEN, {
+ webHook: {
+ port,
+ https: {
+ key: fs.readFileSync(key),
+ cert: fs.readFileSync(cert),
+ },
+ },
+ });
+ return utils.sendWebHookMessage(port, TOKEN, { https: true });
+ });
+ });
+
describe('#initPolling', function initPollingSuite() {
it('initiates polling', function test() {
testbot.initPolling();
@@ -215,7 +245,6 @@ describe('Telegram', function telegramSuite() {
describe('#setWebHook', function setWebHookSuite() {
const ip = '216.58.210.174';
- const cert = `${__dirname}/../examples/crt.pem`;
before(function before() {
utils.handleRatelimit(bot, 'setWebHook', this);
});
diff --git a/test/utils.js b/test/utils.js
index c4b59a9..c63c58e 100644
--- a/test/utils.js
+++ b/test/utils.js
@@ -37,6 +37,7 @@ exports = module.exports = {
* @param {Object} [options]
* @param {String} [options.method=POST] Method to use
* @param {Object} [options.message] Message to send. Default to a generic text message
+ * @param {Boolean} [options.https=false] Use https
* @return {Promise}
*/
sendWebHookMessage,
@@ -136,7 +137,8 @@ function hasOpenWebHook(port, reverse) {
function sendWebHookMessage(port, token, options = {}) {
assert.ok(port);
assert.ok(token);
- const url = `http://127.0.0.1:${port}/bot${token}`;
+ const protocol = options.https ? 'https' : 'http';
+ const url = `${protocol}://127.0.0.1:${port}/bot${token}`;
return request({
url,
method: options.method || 'POST',