diff --git a/src/dbus_main.cpp b/src/dbus_main.cpp
new file mode 100644
index 0000000..6cee92e
--- /dev/null
+++ b/src/dbus_main.cpp
@@ -0,0 +1,455 @@
+#define DBUS_API_SUBJECT_TO_CHANGE
+#include <dbus/dbus.h>
+#include <stdbool.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <iostream>
+#include <string>
+#include <vector>
+#include <boost/iostreams/stream.hpp>
+#include <boost/property_tree/ptree.hpp>
+#include <boost/property_tree/xml_parser.hpp>
+
+/**
+ * Connect to the DBUS bus and send a broadcast signal
+ */
+void sendsignal(char* sigvalue) {
+  DBusMessage* msg;
+  DBusMessageIter args;
+  DBusConnection* conn;
+  DBusError err;
+  int ret;
+  dbus_uint32_t serial = 0;
+
+  printf("Sending signal with value %s\n", sigvalue);
+
+  // initialise the error value
+  dbus_error_init(&err);
+
+  // connect to the DBUS system bus, and check for errors
+  conn = dbus_bus_get(DBUS_BUS_SYSTEM, &err);
+  if (dbus_error_is_set(&err)) {
+    fprintf(stderr, "Connection Error (%s)\n", err.message);
+    dbus_error_free(&err);
+  }
+  if (NULL == conn) {
+    exit(1);
+  }
+
+  // register our name on the bus, and check for errors
+  ret = dbus_bus_request_name(conn, "test.signal.source",
+                              DBUS_NAME_FLAG_REPLACE_EXISTING, &err);
+  if (dbus_error_is_set(&err)) {
+    fprintf(stderr, "Name Error (%s)\n", err.message);
+    dbus_error_free(&err);
+  }
+  if (DBUS_REQUEST_NAME_REPLY_PRIMARY_OWNER != ret) {
+    exit(1);
+  }
+
+  // create a signal & check for errors
+  msg = dbus_message_new_signal(
+      "/test/signal/Object",  // object name of the signal
+      "test.signal.Type",     // interface name of the signal
+      "Test");                // name of the signal
+  if (NULL == msg) {
+    fprintf(stderr, "Message Null\n");
+    exit(1);
+  }
+
+  // append arguments onto signal
+  dbus_message_iter_init_append(msg, &args);
+  if (!dbus_message_iter_append_basic(&args, DBUS_TYPE_STRING, &sigvalue)) {
+    fprintf(stderr, "Out Of Memory!\n");
+    exit(1);
+  }
+
+  // send the message and flush the connection
+  if (!dbus_connection_send(conn, msg, &serial)) {
+    fprintf(stderr, "Out Of Memory!\n");
+    exit(1);
+  }
+  dbus_connection_flush(conn);
+
+  printf("Signal Sent\n");
+
+  // free the message and close the connection
+  dbus_message_unref(msg);
+  dbus_connection_close(conn);
+}
+
+/**
+ * Call a method on a remote object
+ */
+void query(const char* param) {
+  DBusMessage* msg;
+  DBusMessageIter args;
+  DBusConnection* conn;
+  DBusError err;
+  DBusPendingCall* pending;
+  int ret;
+  bool stat;
+  dbus_uint32_t level;
+
+  printf("Calling remote method with %s\n", param);
+
+  // initialiset the errors
+  dbus_error_init(&err);
+
+  // connect to the system bus and check for errors
+  conn = dbus_bus_get(DBUS_BUS_SYSTEM, &err);
+  if (dbus_error_is_set(&err)) {
+    fprintf(stderr, "Connection Error (%s)\n", err.message);
+    dbus_error_free(&err);
+  }
+  if (NULL == conn) {
+    exit(1);
+  }
+  /*
+  // request our name on the bus
+  ret = dbus_bus_request_name(conn, "test.method.caller",
+  DBUS_NAME_FLAG_REPLACE_EXISTING , &err);
+  if (dbus_error_is_set(&err)) {
+     fprintf(stderr, "Name Error (%s)\n", err.message);
+     dbus_error_free(&err);
+  }
+  if (DBUS_REQUEST_NAME_REPLY_PRIMARY_OWNER != ret) {
+     exit(1);
+  }
+  */
+
+  // create a new method call and check for errors
+  msg = dbus_message_new_method_call(
+      "org.freedesktop.Avahi",         // target for the method call
+      "/",                             // object to call on
+      "org.freedesktop.Avahi.Server",  // interface to call on
+      "GetHostName");                  // method name
+  if (NULL == msg) {
+    fprintf(stderr, "Message Null\n");
+    exit(1);
+  }
+
+  // append arguments
+  /*
+  dbus_message_iter_init_append(msg, &args);
+  if (!dbus_message_iter_append_basic(&args, DBUS_TYPE_STRING, &param)) {
+     fprintf(stderr, "Out Of Memory!\n");
+     exit(1);
+  }
+  */
+  // send message and get a handle for a reply
+  if (!dbus_connection_send_with_reply(conn, msg, &pending,
+                                       -1)) {  // -1 is default timeout
+    fprintf(stderr, "Out Of Memory!\n");
+    exit(1);
+  }
+  if (NULL == pending) {
+    fprintf(stderr, "Pending Call Null\n");
+    exit(1);
+  }
+  dbus_connection_flush(conn);
+
+  printf("Request Sent\n");
+
+  // free message
+  dbus_message_unref(msg);
+
+  // block until we recieve a reply
+  dbus_pending_call_block(pending);
+
+  // get the reply message
+  msg = dbus_pending_call_steal_reply(pending);
+  if (NULL == msg) {
+    fprintf(stderr, "Reply Null\n");
+    exit(1);
+  }
+  // free the pending message handle
+  dbus_pending_call_unref(pending);
+
+  // read the parameters
+  char* str = NULL;
+  if (!dbus_message_iter_init(msg, &args))
+    fprintf(stderr, "Message has no arguments!\n");
+  else if (DBUS_TYPE_STRING != dbus_message_iter_get_arg_type(&args))
+    fprintf(stderr, "Argument is not boolean!\n");
+  else
+    dbus_message_iter_get_basic(&args, &str);
+
+  printf("Got Reply: %s\n", str);
+
+  // free reply and close connection
+  dbus_message_unref(msg);
+  dbus_connection_close(conn);
+}
+
+void list_names() {
+  DBusError err;
+
+  int ret;
+  bool stat;
+  dbus_uint32_t level;
+
+  // initialiset the errors
+  dbus_error_init(&err);
+
+  // connect to the system bus and check for errors
+  DBusConnection* conn = dbus_bus_get(DBUS_BUS_SYSTEM, &err);
+  if (dbus_error_is_set(&err)) {
+    fprintf(stderr, "Connection Error (%s)\n", err.message);
+    dbus_error_free(&err);
+  }
+  if (NULL == conn) {
+    exit(1);
+  }
+
+  // create a new method call and check for errors
+  DBusMessage* msg = dbus_message_new_method_call(
+      "org.freedesktop.DBus",  // target for the method call
+      "/",                     // object to call on
+      "org.freedesktop.DBus",  // interface to call on
+      "ListNames");            // method name
+  if (NULL == msg) {
+    fprintf(stderr, "Message Null\n");
+    exit(1);
+  }
+
+  DBusPendingCall* pending;
+  // send message and get a handle for a reply
+  if (!dbus_connection_send_with_reply(conn, msg, &pending,
+                                       -1)) {  // -1 is default timeout
+    fprintf(stderr, "Out Of Memory!\n");
+    exit(1);
+  }
+  if (NULL == pending) {
+    fprintf(stderr, "Pending Call Null\n");
+    exit(1);
+  }
+  dbus_connection_flush(conn);
+
+  // free message
+  dbus_message_unref(msg);
+
+  // block until we recieve a reply
+  dbus_pending_call_block(pending);
+
+  // get the reply message
+  msg = dbus_pending_call_steal_reply(pending);
+  if (NULL == msg) {
+    fprintf(stderr, "Reply Null\n");
+    exit(1);
+  }
+  // free the pending message handle
+  dbus_pending_call_unref(pending);
+
+  // read the parameters
+  DBusMessageIter args;
+  DBusMessageIter strings;
+  char* paths = NULL;
+  if (!dbus_message_iter_init(msg, &args)) {
+    fprintf(stderr, "Message has no arguments!\n");
+  }
+  std::vector<std::string> names;
+  do {
+    dbus_message_iter_recurse(&args, &strings);
+    do {
+      dbus_message_iter_get_basic(&strings, &paths);
+      names.emplace_back(paths);
+    } while (dbus_message_iter_next(&strings));
+  } while (dbus_message_iter_next(&args));
+
+  // free reply and close connection
+  dbus_message_unref(msg);
+  dbus_connection_close(conn);
+}
+
+std::vector<std::string> read_dbus_xml_names(std::string& xml_data) {
+  std::vector<std::string> values;
+  // populate tree structure pt
+  using boost::property_tree::ptree;
+  ptree pt;
+  boost::iostreams::stream<boost::iostreams::array_source> stream(
+      xml_data.c_str(), xml_data.size());
+  read_xml(stream, pt);
+
+  // traverse node to find other nodes
+  for (const auto& interface : pt.get_child("node")) {
+    if (interface.first == "node") {
+      auto t = interface.second.get<std::string>("<xmlattr>", "default");
+      for (const auto& subnode : interface.second.get_child("<xmlattr>")) {
+        if (subnode.first == "name") {
+          auto t = subnode.second.get("", "unknown");
+          values.emplace_back(std::move(t));
+        }
+      }
+    }
+  }
+  return values;
+}
+
+using sensor_values=std::vector<std::pair<std::string, int32_t>>;
+
+sensor_values read_sensor_values() {
+  sensor_values values;
+  DBusError err;
+
+  int ret;
+  bool stat;
+  dbus_uint32_t level;
+
+  // initialiset the errors
+  dbus_error_init(&err);
+
+  // connect to the system bus and check for errors
+  DBusConnection* conn = dbus_bus_get(DBUS_BUS_SYSTEM, &err);
+  if (dbus_error_is_set(&err)) {
+    fprintf(stderr, "Connection Error (%s)\n", err.message);
+    dbus_error_free(&err);
+  }
+  if (NULL == conn) {
+    exit(1);
+  }
+
+  // create a new method call and check for errors
+  DBusMessage* msg = dbus_message_new_method_call(
+      "org.openbmc.Sensors",                  // target for the method call
+      "/org/openbmc/sensors/tach",            // object to call on
+      "org.freedesktop.DBus.Introspectable",  // interface to call on
+      "Introspect");                          // method name
+  if (NULL == msg) {
+    fprintf(stderr, "Message Null\n");
+    exit(1);
+  }
+
+  DBusPendingCall* pending;
+  // send message and get a handle for a reply
+  if (!dbus_connection_send_with_reply(conn, msg, &pending,
+                                       -1)) {  // -1 is default timeout
+    fprintf(stderr, "Out Of Memory!\n");
+    exit(1);
+  }
+  if (NULL == pending) {
+    fprintf(stderr, "Pending Call Null\n");
+    exit(1);
+  }
+  dbus_connection_flush(conn);
+
+  // free message
+  dbus_message_unref(msg);
+
+  // block until we recieve a reply
+  dbus_pending_call_block(pending);
+
+  // get the reply message
+  msg = dbus_pending_call_steal_reply(pending);
+  if (NULL == msg) {
+    fprintf(stderr, "Reply Null\n");
+    exit(1);
+  }
+  // free the pending message handle
+  dbus_pending_call_unref(pending);
+
+  // read the parameters
+  DBusMessageIter args;
+  char* xml_struct = NULL;
+  if (!dbus_message_iter_init(msg, &args)) {
+    fprintf(stderr, "Message has no arguments!\n");
+  }
+
+  // read the arguments
+  if (!dbus_message_iter_init(msg, &args)) {
+    fprintf(stderr, "Message has no arguments!\n");
+  } else if (DBUS_TYPE_STRING != dbus_message_iter_get_arg_type(&args)) {
+    fprintf(stderr, "Argument is not string!\n");
+  } else {
+    dbus_message_iter_get_basic(&args, &xml_struct);
+  }
+  std::vector<std::string> methods;
+  if (xml_struct != NULL) {
+    std::string xml_data(xml_struct);
+    methods = read_dbus_xml_names(xml_data);
+  }
+
+  fprintf(stdout, "Found %ld sensors \n", methods.size());
+
+  for (auto& method : methods) {
+    // TODO(Ed) make sure sensor exposes SensorValue interface
+    // create a new method call and check for errors
+    DBusMessage* msg = dbus_message_new_method_call(
+        "org.openbmc.Sensors",                  // target for the method call
+        ("/org/openbmc/sensors/tach/" + method).c_str(),  // object to call on
+        "org.openbmc.SensorValue",              // interface to call on
+        "getValue");                            // method name
+    if (NULL == msg) {
+      fprintf(stderr, "Message Null\n");
+      exit(1);
+    }
+
+    DBusPendingCall* pending;
+    // send message and get a handle for a reply
+    if (!dbus_connection_send_with_reply(conn, msg, &pending,
+                                         -1)) {  // -1 is default timeout
+      fprintf(stderr, "Out Of Memory!\n");
+      exit(1);
+    }
+    if (NULL == pending) {
+      fprintf(stderr, "Pending Call Null\n");
+      exit(1);
+    }
+    dbus_connection_flush(conn);
+
+    // free message
+    dbus_message_unref(msg);
+
+    // block until we recieve a reply
+    dbus_pending_call_block(pending);
+
+    // get the reply message
+    msg = dbus_pending_call_steal_reply(pending);
+    if (NULL == msg) {
+      fprintf(stderr, "Reply Null\n");
+      exit(1);
+    }
+    // free the pending message handle
+    dbus_pending_call_unref(pending);
+
+    // read the parameters
+    DBusMessageIter args;
+    int32_t value;
+    if (!dbus_message_iter_init(msg, &args)) {
+      fprintf(stderr, "Message has no arguments!\n");
+    }
+
+    // read the arguments
+    if (!dbus_message_iter_init(msg, &args)) {
+      fprintf(stderr, "Message has no arguments!\n");
+    } else if (DBUS_TYPE_VARIANT != dbus_message_iter_get_arg_type(&args)) {
+      fprintf(stderr, "Argument is not string!\n");
+    } else {
+      DBusMessageIter sub;
+      dbus_message_iter_recurse(&args, &sub);
+      auto type = dbus_message_iter_get_arg_type(&sub);
+      if (DBUS_TYPE_INT32 != type) {
+        fprintf(stderr, "Variant subType is not int32 it is %d\n", type);
+      } else {
+        dbus_message_iter_get_basic(&sub, &value);
+        values.emplace_back(method.c_str(), value);
+      }
+    }
+  }
+
+  // free reply and close connection
+  dbus_message_unref(msg);
+  return values;
+}
+
+
+int main(int argc, char** argv) {
+  auto values = read_sensor_values();
+
+  for (auto value: values){
+    std::cout << value.first << ": " << value.second << "\n";
+  }
+
+  return 0;
+}
\ No newline at end of file
diff --git a/src/test_resources/blns.txt b/src/test_resources/blns
similarity index 100%
rename from src/test_resources/blns.txt
rename to src/test_resources/blns
diff --git a/src/webserver_main.cpp b/src/webserver_main.cpp
index 2ec7e37..82b83a7 100644
--- a/src/webserver_main.cpp
+++ b/src/webserver_main.cpp
@@ -31,11 +31,196 @@
 #include <boost/asio.hpp>
 #include <boost/endian/arithmetic.hpp>
 
+#include <dbus/dbus.h>
+#include <boost/iostreams/stream.hpp>
+#include <boost/property_tree/ptree.hpp>
+#include <boost/property_tree/xml_parser.hpp>
+
 #include <iostream>
 #include <memory>
 #include <string>
 #include <unordered_set>
 
+using sensor_values = std::vector<std::pair<std::string, int32_t>>;
+
+std::vector<std::string> read_dbus_xml_names(std::string& xml_data) {
+  std::vector<std::string> values;
+  // populate tree structure pt
+  using boost::property_tree::ptree;
+  ptree pt;
+  boost::iostreams::stream<boost::iostreams::array_source> stream(
+      xml_data.c_str(), xml_data.size());
+  read_xml(stream, pt);
+
+  // traverse node to find other nodes
+  for (const auto& interface : pt.get_child("node")) {
+    if (interface.first == "node") {
+      auto t = interface.second.get<std::string>("<xmlattr>", "default");
+      for (const auto& subnode : interface.second.get_child("<xmlattr>")) {
+        if (subnode.first == "name") {
+          auto t = subnode.second.get("", "unknown");
+          values.emplace_back(std::move(t));
+        }
+      }
+    }
+  }
+  return values;
+}
+
+sensor_values read_sensor_values() {
+  sensor_values values;
+  DBusError err;
+
+  int ret;
+  bool stat;
+  dbus_uint32_t level;
+
+  // initialiset the errors
+  dbus_error_init(&err);
+
+  // connect to the system bus and check for errors
+  DBusConnection* conn = dbus_bus_get(DBUS_BUS_SYSTEM, &err);
+  if (dbus_error_is_set(&err)) {
+    fprintf(stderr, "Connection Error (%s)\n", err.message);
+    dbus_error_free(&err);
+  }
+  if (NULL == conn) {
+    exit(1);
+  }
+
+  // create a new method call and check for errors
+  DBusMessage* msg = dbus_message_new_method_call(
+      "org.openbmc.Sensors",                  // target for the method call
+      "/org/openbmc/sensors/tach",            // object to call on
+      "org.freedesktop.DBus.Introspectable",  // interface to call on
+      "Introspect");                          // method name
+  if (NULL == msg) {
+    fprintf(stderr, "Message Null\n");
+    exit(1);
+  }
+
+  DBusPendingCall* pending;
+  // send message and get a handle for a reply
+  if (!dbus_connection_send_with_reply(conn, msg, &pending,
+                                       -1)) {  // -1 is default timeout
+    fprintf(stderr, "Out Of Memory!\n");
+    exit(1);
+  }
+  if (NULL == pending) {
+    fprintf(stderr, "Pending Call Null\n");
+    exit(1);
+  }
+  dbus_connection_flush(conn);
+
+  // free message
+  dbus_message_unref(msg);
+
+  // block until we recieve a reply
+  dbus_pending_call_block(pending);
+
+  // get the reply message
+  msg = dbus_pending_call_steal_reply(pending);
+  if (NULL == msg) {
+    fprintf(stderr, "Reply Null\n");
+    exit(1);
+  }
+  // free the pending message handle
+  dbus_pending_call_unref(pending);
+
+  // read the parameters
+  DBusMessageIter args;
+  char* xml_struct = NULL;
+  if (!dbus_message_iter_init(msg, &args)) {
+    fprintf(stderr, "Message has no arguments!\n");
+  }
+
+  // read the arguments
+  if (!dbus_message_iter_init(msg, &args)) {
+    fprintf(stderr, "Message has no arguments!\n");
+  } else if (DBUS_TYPE_STRING != dbus_message_iter_get_arg_type(&args)) {
+    fprintf(stderr, "Argument is not string!\n");
+  } else {
+    dbus_message_iter_get_basic(&args, &xml_struct);
+  }
+  std::vector<std::string> methods;
+  if (xml_struct != NULL) {
+    std::string xml_data(xml_struct);
+    methods = read_dbus_xml_names(xml_data);
+  }
+
+  fprintf(stdout, "Found %ld sensors \n", methods.size());
+
+  for (auto& method : methods) {
+    // TODO(Ed) make sure sensor exposes SensorValue interface
+    // create a new method call and check for errors
+    DBusMessage* msg = dbus_message_new_method_call(
+        "org.openbmc.Sensors",  // target for the method call
+        ("/org/openbmc/sensors/tach/" + method).c_str(),  // object to call on
+        "org.openbmc.SensorValue",  // interface to call on
+        "getValue");                // method name
+    if (NULL == msg) {
+      fprintf(stderr, "Message Null\n");
+      exit(1);
+    }
+
+    DBusPendingCall* pending;
+    // send message and get a handle for a reply
+    if (!dbus_connection_send_with_reply(conn, msg, &pending,
+                                         -1)) {  // -1 is default timeout
+      fprintf(stderr, "Out Of Memory!\n");
+      exit(1);
+    }
+    if (NULL == pending) {
+      fprintf(stderr, "Pending Call Null\n");
+      exit(1);
+    }
+    dbus_connection_flush(conn);
+
+    // free message
+    dbus_message_unref(msg);
+
+    // block until we recieve a reply
+    dbus_pending_call_block(pending);
+
+    // get the reply message
+    msg = dbus_pending_call_steal_reply(pending);
+    if (NULL == msg) {
+      fprintf(stderr, "Reply Null\n");
+      exit(1);
+    }
+    // free the pending message handle
+    dbus_pending_call_unref(pending);
+
+    // read the parameters
+    DBusMessageIter args;
+    int32_t value;
+    if (!dbus_message_iter_init(msg, &args)) {
+      fprintf(stderr, "Message has no arguments!\n");
+    }
+
+    // read the arguments
+    if (!dbus_message_iter_init(msg, &args)) {
+      fprintf(stderr, "Message has no arguments!\n");
+    } else if (DBUS_TYPE_VARIANT != dbus_message_iter_get_arg_type(&args)) {
+      fprintf(stderr, "Argument is not string!\n");
+    } else {
+      DBusMessageIter sub;
+      dbus_message_iter_recurse(&args, &sub);
+      auto type = dbus_message_iter_get_arg_type(&sub);
+      if (DBUS_TYPE_INT32 != type) {
+        fprintf(stderr, "Variant subType is not int32 it is %d\n", type);
+      } else {
+        dbus_message_iter_get_basic(&sub, &value);
+        values.emplace_back(method.c_str(), value);
+      }
+    }
+  }
+
+  // free reply and close connection
+  dbus_message_unref(msg);
+  return values;
+}
+
 int main(int argc, char** argv) {
   auto worker(g3::LogWorker::createLogWorker());
   std::string logger_name("bmcweb");
@@ -114,6 +299,18 @@
         conn.send_binary(str);
 
       });
+
+  CROW_ROUTE(app, "/sensortest")
+  ([]() {
+    crow::json::wvalue j;
+    auto values = read_sensor_values();
+    for (auto& pair : values) {
+      j[pair.first] = pair.second;
+    }
+
+    return j;
+  });
+
   auto ssl_context = ensuressl::get_ssl_context(ssl_pem_file);
   app.port(18080)
       //.ssl(std::move(ssl_context))
