Skip to content

Instantly share code, notes, and snippets.

@MassimoSporchia
Forked from h0ru5/main.js
Created May 1, 2020 08:15
Show Gist options
  • Save MassimoSporchia/5ce35f2fdaa3209e675229a195140164 to your computer and use it in GitHub Desktop.
Save MassimoSporchia/5ce35f2fdaa3209e675229a195140164 to your computer and use it in GitHub Desktop.
connecting to AWS IoT through a HTTP CONNECT
const {toProxyOpts, proxyConnect } = require("./proxy-connect")
// using it to connect to AWS IoT through a HTTP CONNECT proxy
const aws = require("aws-iot-device-sdk");
const proxyUrl = process.env.http_proxy || "http://localhost:3128/";
const opts = {
keyPath: "assets/device.private.key",
certPath: "assets/device.cert.pem",
caPath: "assets/root-CA.crt",
host: "data.iot.eu-central-1.amazonaws.com",
clientId: "deviceName",
port: 443,
ALPNProtocols: ["x-amzn-mqtt-ca"],
proxy: toProxyOpts(proxyUrl)
};
const callBack = socket => {
let MQTTopts = opts;
MQTTopts.socket = socket;
const device = new aws.device(MQTTopts);
device.on("connect", () => {
console.log("connected");
device.subscribe("broadcast");
});
};
proxyConnect(opts, callBack);
const net = require("net");
const url = require("url");
const toProxyOpts = (proxy) => {
let proxyopts = proxy || {};
if (typeof proxy === "string") {
proxyopts = url.parse(proxy);
}
if (!proxyopts.port) {
proxyopts.port = 8080;
}
proxyopts.host = proxyopts.hostname || proxyopts.host;
if (proxyopts.host && proxyopts.path) {
// if both a `host` and `path` are specified then it's most likely the
// result of a `url.parse()` call... we need to remove the `path` portion so
// that `net.connect()` doesn't attempt to open that as a unix socket file.
delete proxyopts.path;
delete proxyopts.pathname;
}
return proxyopts;
};
const proxyConnect = (opts, getFunky) => {
let buffers = [];
let buffersLength = 0;
const read = () => {
let b = proxySocket.read();
if (b) proxyData(b);
else proxySocket.once("readable", read);
};
const writeRequest = socket => {
let hostname = opts.host + ":" + opts.port;
let msg = "CONNECT " + hostname + " HTTP/1.1\r\n";
socket.write(msg + "\r\n");
};
const proxyData = b => {
buffers.push(b);
buffersLength += b.length;
var buffered = Buffer.concat(buffers, buffersLength);
var str = buffered.toString("ascii");
if (!~str.indexOf("\r\n\r\n")) {
// keep buffering
debug("have not received end of HTTP headers yet...");
if (proxySocket.read) {
read();
} else {
proxySocket.once("data", ondata);
}
return;
}
var firstLine = str.substring(0, str.indexOf("\r\n"));
var statusCode = +firstLine.split(" ")[1];
if (200 == statusCode) {
connectTLS();
}
};
const connectTLS = () => {
console.log("proxy connected us...");
// nullify the buffered data since we won't be needing it
buffers = buffered = null;
// this socket now is forwarded to destination host
getFunky(proxySocket);
};
let proxySocket = net.connect(opts.proxy);
if (proxySocket.read) {
read();
} else {
proxySocket.once("data", proxyData);
}
writeRequest(proxySocket);
};
module.exports = {
toProxyOpts,
proxyConnect
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment