diff --git a/chronos_npm_package/README.md b/chronos_npm_package/README.md index 779c893fb..0442f28ae 100644 --- a/chronos_npm_package/README.md +++ b/chronos_npm_package/README.md @@ -1,13 +1,15 @@ ## What's New? + - Enhanced Metrics Collection: Docker now supports Prometheus metrics scraping, offering improved monitoring capabilities - Streamlined Visualization: Docker and Kubernetes integrate with Grafana to provide dynamic visualization of collected metrics -- Kubernetes graph type customization and resource data processing +- Kubernetes graph type customization and resource data processing - Bug Fixes - Refactored code for additional modularity and customization # -## Features +## Features + - Distributed tracing enabled across microservice applications - Supports PostgreSQL and MongoDB databases - Displays real-time temperature, speed, latency, and memory statistics @@ -18,18 +20,20 @@ # ## Using Chronos + The following steps should be performed in each microservice you want to track unless otherwise noted. ### 1. Install Chronos Tracker + Install the package as a dependency in each of the microservices you want to track: ``` npm install @chronosmicro/tracker ``` - ### 2. Configuring Chronos Tracker -Create a `chronos-config.js` file, which exports a JavaScript object with required Chronos configuration parameters. Use this configuration to customize Chronos for your specific microservice environment. + +Create a `chronos-config.js` file, which exports a JavaScript object with required Chronos configuration parameters. Use this configuration to customize Chronos for your specific microservice environment. ```js // A sample `chronos-config.js` file @@ -42,21 +46,21 @@ module.exports = { // Database Information database: { - connection: 'REST', // Choose 'REST' or 'gRPC' for your connection type - type: 'MongoDB', // Choose 'MongoDB' or 'PostgreSQL' - URI: '', // should be a connection string to the database where you intend Chronos to write and record data regarding health, HTTP route tracing, and container infomation + connection: 'REST', // Choose 'REST' or 'gRPC' for your connection type + type: 'MongoDB', // Choose 'MongoDB' or 'PostgreSQL' + URI: '', // should be a connection string to the database where you intend Chronos to write and record data regarding health, HTTP route tracing, and container infomation }, /* USE ONLY ONE OF THE CONFIGURATIONS BELOW: */ // (a) Microservices Mode mode: 'microservices', - dockerized: false, // set to true if your service is Dockerized + dockerized: false, // set to true if your service is Dockerized // (b) Kubernetes mode: 'kubernetes', promService: 'prometheus-service', // Prometheus service name promPort: 8080, //Prometheus service port - grafanaAPIKey: process.env.CHRONOS_GRAFANA_API_KEY,//API for Grafana + grafanaAPIKey: process.env.CHRONOS_GRAFANA_API_KEY, //API for Grafana // (c) Apache Kafka mode: 'kafka', @@ -68,36 +72,39 @@ module.exports = { promPort: 9090, //Prometheus service port grafanaAPIKey: process.env.CHRONOS_GRAFANA_API_KEY, //API key for Grafana - - // Notifications //Add notification configurations here notifications: [], -} +}; ``` + Note: Consider using a `.env` file to securely store sensitive parameters like database URIs. ### 3. Configuring notifications -The `notifications` property is an array that can be optionally left empty. It allows developers to be alerted when the server responds to requests with status codes >= 400. To set up notifications, set the value of the `notifications` property to an array of objects, each with a `type` and `settings` property. + +The `notifications` property is an array that can be optionally left empty. It allows developers to be alerted when the server responds to requests with status codes >= 400. To set up notifications, set the value of the `notifications` property to an array of objects, each with a `type` and `settings` property. Chronos only supports **Slack** and **email** notifications at this time. **Slack** + ```js // ... notifications: [ { type: 'slack', settings: { - slackurl: process.env.WEBHOOK - } - } -] + slackurl: process.env.WEBHOOK, + }, + }, +]; // ... ``` + Chronos uses the Slack API to send messages to a Slack channel and only requires the **webhook url**. Learn how to set up [Slack webhooks](https://api.slack.com/messaging/webhooks) for your team. **Email** + ```js // ... notifications: [ @@ -105,47 +112,49 @@ notifications: [ type: 'email', settings: { emails: 'foobar@email.com, bizbaz@email.edu', //can be single or multiple, separated by a comma - emailHost: 'smpt@gmail.com',// the smtp host of your email server + emailHost: 'smpt@gmail.com', // the smtp host of your email server emailPort: 465, // the email port is either **465** or **587** depending on the sender email security settings. Learn more about email ports by reading the [nodemailer docs](https://nodemailer.com/smtp/) user: process.env.SENDER_EMAIL, //email address of the sender - password: process.env.SENDER_PASSWORD //password of the sender's email - } - } -] + password: process.env.SENDER_PASSWORD, //password of the sender's email + }, + }, +]; ``` +### 4. Utilize `chronos-config.js` in your application +To integrate the `chronos-config.js` file into your application, follow these steps: + +1. importing the `chronos-config.js` file -### 4. Utilize `chronos-config.js` in your application -To integrate the `chronos-config.js` file into your application, follow these steps: - 1. importing the `chronos-config.js` file ```js const chronosConfig = require('./chronos-config.js'); ``` - 2. importing the Chronos class + +2. importing the Chronos class + ```js const Chronos = require('@chronosmicro/tracker'); ``` - 3. creating a new instance of the Chronos class + +3. creating a new instance of the Chronos class + ```js const chronos = new Chronos(chronosConfig); ``` # -### Mode Specific Configurations - +### Mode Specific Configurations ### A. Chronos Tracker for "Microservices" Mode -In the `microservices` mode, Chronos employs the `dockerized` setting to determine the operational environment of the microservice. - - * `dockerized`: This setting is crucial for specifying the nature of the service deployment. - * Default Setting: If `dockerized` is not explicitly set to true, Chronos defaults to assuming that the service is not operating in a Docker container environment. Hence, the default value of `dockerized` is false. - * When `dockerized` is `false`: This configuration tells Chronos to collect metrics directly from the host system. It's applicable for services running outside of Docker containers. - * When `dockerized` is `true`: This configuration directs Chronos to retrieve metrics from the Docker daemon, aligning with services deployed within Docker containers for accurate monitoring. - +In the `microservices` mode, Chronos employs the `dockerized` setting to determine the operational environment of the microservice. +- `dockerized`: This setting is crucial for specifying the nature of the service deployment. + - Default Setting: If `dockerized` is not explicitly set to true, Chronos defaults to assuming that the service is not operating in a Docker container environment. Hence, the default value of `dockerized` is false. + - When `dockerized` is `false`: This configuration tells Chronos to collect metrics directly from the host system. It's applicable for services running outside of Docker containers. + - When `dockerized` is `true`: This configuration directs Chronos to retrieve metrics from the Docker daemon, aligning with services deployed within Docker containers for accurate monitoring. ```js // Excerpt from a chronos-config.js @@ -154,10 +163,10 @@ module.exports = { // ... mode: 'microservices', - dockerized: false, // false or true + dockerized: false, // false or true // ... -} +}; ``` Once your `chronos-config.js` file is setup, use Chronos in your microservice by importing the config, creating a new instance of the class, and calling the `Chronos.track` method to start saving health metrics: @@ -166,7 +175,7 @@ Once your `chronos-config.js` file is setup, use Chronos in your microservice by const chronosConfig = require('./chronos-config.js'); const Chronos = require('@chronosmicro/tracker'); const chronos = new Chronos(chronosConfig); -chronos.track() +chronos.track(); ``` If you are using an Express.js REST API, calling `Chronos.track()` returns middleware that allows users to track incoming network requests and their corresponding outgoing responses by marking them with unique IDs using `Chronos.propagate`. @@ -185,18 +194,21 @@ const app = express(); const trackingMiddleware = chronos.track(); // Pass all requests through this middleware, which always calls next() to allow all requests to continue on to match other routes -app.use('/', trackingMiddleware); +app.use('/', trackingMiddleware); ``` #### Special Notes on Dockerized Microservices + **IMPORTANT:** Give your containers the same names you pass in as arguments for microservice names. In order to have container statistics saved to your database along with other health info, bind volumes to this path when starting up the containers: + ``` /var/run/docker.sock ``` For example, you can type the following when starting up a container: + ``` docker run -v /var/run/docker.sock:/var/run/docker.sock [your-image-tag] ``` @@ -208,10 +220,10 @@ volumes: - "/var/run/docker.sock:/var/run/docker.sock" ``` -Check out the [**Microservices Readme**](../examples_new/README.md). # ### B. Chronos Tracker for "Kubernetes" Mode + Chronos monitors Kubernetes clusters in two steps. First, it saves metric data from instant queries to a Prometheus server in your Kubernetes cluster. Then, it displays all metrics data through Grafana dashboards. In `chronos-config.js`, set the `mode` to `kubernetes` and pass it both the name of the port the Prometheus server is listening on INSIDE the cluster, and the name of the Prometheus service so that its IP address can be resolved using KubeDNS. @@ -231,8 +243,7 @@ module.exports = { grafanaAPIKey: process.env.CHRONOS_GRAFANA_API_KEY, // ... -} - +}; ``` Then, insert the code below into a **SINGLE** microservice that will be deployed only as a **SINGLE** pod (to avoid saving the same metrics as queried by multiple pods), call `Chronos.kuberbetes`: @@ -244,10 +255,11 @@ const chronos = new Chronos(chronosConfig); chronos.kubernetes(); ``` -Check out the [**Kubernetes Readme**](../examples/kubernetes/README.md). + # ### C. Chronos Tracker for "Kafka" Mode + Chronos can monitor an Apache Kafka cluster via JMX to Prometheus Exporter. In order for this feature to work you must be running [JMX to Prometheus Exporter](https://github.com/prometheus/jmx_exporter) either as a Java Agent with your cluster or as a standalone HTTP server. Then, use `chronos-config.js` to specifiy where to retrieve the metrics. @@ -263,10 +275,11 @@ module.exports = { jmxuri: 'http://localhost:12345/metrics', // ... -} +}; ``` -Then, in **ONE AND ONLY ONE** of your microservices, call `Chronos.kafka`: +Then, in **ONE AND ONLY ONE** of your microservices, call `Chronos.kafka`: + ```js const chronosConfig = require('./chronos-config.js'); const Chronos = require('@chronosmicro/tracker'); @@ -280,7 +293,9 @@ When viewing your information in the Chronos Electron application the data will **NOTE:** We provide a jmx_config.yaml file in the Chronos root folder for use with JMX prometheus that provides some useful baseline metrics to monitor. # + ### D. Chronos Tracker for "Docker" Mode + Chronos monitors Docker containers by storing metric data through instant Prometheus queries within your Docker container environment. In `chronos-config.js`, configure the `mode` parameter to `docker`. Additionally, provide the name of the port where the Prometheus server is actively listening inside the container, and specify the name of the Prometheus service to enable DNS-based resolution of its IP address. @@ -300,8 +315,7 @@ module.exports = { grafanaAPIKey: process.env.CHRONOS_GRAFANA_API_KEY, // ... -} - +}; ``` Then, implement the subsequent code snippet within a **SINGLE** microservice that will be deployed only as a **SINGLE** container, and call `Chronos.docker`: @@ -313,8 +327,9 @@ const chronos = new Chronos(chronosConfig); chronos.docker(); ``` -Check out the [**Docker Readme**](../examples/docker/README.md). + # + ### Chronos Tracker for gRPC To monitor your gRPC server, setup `chronos-config.js` as if it was a standard microservices example, but be sure to set the `connection` type to `gRPC`. @@ -326,32 +341,33 @@ module.exports = { // Database Information database: { - connection: 'gRPC', // 'REST' or 'gRPC' - type: 'MongoDB', // 'MongoDB' or 'PostgreSQL' - URI: '', // + connection: 'gRPC', // 'REST' or 'gRPC' + type: 'MongoDB', // 'MongoDB' or 'PostgreSQL' + URI: '', // }, mode: 'microservices', - dockerized: false, // false or true + dockerized: false, // false or true // ... -} +}; ``` Then require in the `chronos-config.js` and `Chronos` and call `Chronos.track` to start tracking health metrics. + ```js - // Example of gRPC server +// Example of gRPC server const chronosConfig = require('./chronos-config.js'); const Chronos = require('@chronosmicro/tracker'); const chronos = new Chronos(chronosConfig); -chronos.track() +chronos.track(); const server = new grpc.Server(); -server.bindAsync("127.0.0.1:30044", grpc.ServerCredentials.createInsecure(), () => { +server.bindAsync('127.0.0.1:30044', grpc.ServerCredentials.createInsecure(), () => { server.start(); - console.log("Server running at http://127.0.0.1:30044"); + console.log('Server running at http://127.0.0.1:30044'); }); ``` @@ -375,27 +391,25 @@ const bookClient = new OrderToBookService('localhost:30044', grpc.credentials.cr const ClientWrapper = chronos.ClientWrapper(bookClient, OrderToBookService); ``` -Next wrap the gRPC server using Chronos +Next wrap the gRPC server using Chronos ```js - - const ServerWrapper = chronos.ServerWrapper(server, Proto.protoname.service, { - AddBook: (call, callback) => { +const ServerWrapper = chronos.ServerWrapper(server, Proto.protoname.service, { + AddBook: (call, callback) => { // console.log(call.metadata) // get the properties from the gRPC client call - const { title, author, numberOfPages, publisher, bookID } = call.request; + const { title, author, numberOfPages, publisher, bookID } = call.request; // create a book in our book collection - BookModel.create({ - title, - author, - numberOfPages, - publisher, - bookID, - }); - callback(null, {}); - }, - }); - + BookModel.create({ + title, + author, + numberOfPages, + publisher, + bookID, + }); + callback(null, {}); + }, +}); ``` For any request you wish to trace, require uuidv4 and write the following code where the initial gRPC request begins, @@ -413,38 +427,42 @@ and then, invoke createMeta as a third argument to any client method that is the ```js orderClient.AddOrder( - order, - (err, data) => { - if (err !== null) { - console.log(err); - // could not add order because bookID does not exist - return res.sendStatus(404); - } - console.log('addOrder response: ', data); - return res.sendStatus(200); - }, - createMeta() - ); - + order, + (err, data) => { + if (err !== null) { + console.log(err); + // could not add order because bookID does not exist + return res.sendStatus(404); + } + console.log('addOrder response: ', data); + return res.sendStatus(200); + }, + createMeta() +); ``` + Finally, on all servers that will be involved in the request path, invoke `chronos.link` with parameters of `client` and `ServerWrapper` in the server wrapper. ```js chronos.link(client, ServerWrapper); ``` -Check out the [**gRPC README**](../examples/gRPC/README.md). # ### Viewing Chronos Data -Once you have configured and intialized Chronos Tracker, it will automatically record monitoring data when your servers are running. The data will be saved into your database of choice, and then start the Chronos desktop app to view by cloning our [GitHub repo](https://github.com/open-source-labs/Chronos). Folow the ReadMe in that repo to setup the Chronos desktop app. + +Once you have configured and intialized Chronos Tracker, it will automatically record monitoring data when your servers are running. The data will be saved into your database of choice, and then start the Chronos desktop app to view by cloning our [GitHub repo](https://github.com/open-source-labs/Chronos). Folow the ReadMe in that repo to setup the Chronos desktop app. # + ## Examples We provide working example microservice applications in Chronos desktop app repo in the [**examples**](../chronos_npm_package/README.md) folder. + # + ## Technologies + - Electron - JavaScript - TypeScript @@ -460,6 +478,7 @@ We provide working example microservice applications in Chronos desktop app repo - Kubernetes # + ## Contributing Chronos hopes to inspire an active community of both users and developers. For questions, comments, or contributions, please submit a pull request. @@ -467,8 +486,11 @@ Chronos hopes to inspire an active community of both users and developers. For q Read our [contributing README](../../CONTRIBUTING.md) to further learn how you can take part in improving Chronos. # + ## License [MIT](https://github.com/oslabs-beta/Chronos/blob/master/LICENSE.md) + # + ###### Return to [Top](#whats-new) diff --git a/chronos_npm_package/package-lock.json b/chronos_npm_package/package-lock.json index 2cd77db60..b29b49cc1 100644 --- a/chronos_npm_package/package-lock.json +++ b/chronos_npm_package/package-lock.json @@ -1,12 +1,12 @@ { "name": "@chronosmicro/tracker", - "version": "12.0.1", + "version": "12.0.3", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "@chronosmicro/tracker", - "version": "12.0.1", + "version": "12.0.3", "license": "ISC", "dependencies": { "@grpc/grpc-js": "^1.8.0", diff --git a/chronos_npm_package/package.json b/chronos_npm_package/package.json index 0e8f9ccd1..15226a8a8 100644 --- a/chronos_npm_package/package.json +++ b/chronos_npm_package/package.json @@ -1,6 +1,6 @@ { "name": "@chronosmicro/tracker", - "version": "12.0.2", + "version": "12.0.4", "description": "Chronos microservice metrics tracker", "main": "chronos.js", "scripts": { diff --git a/examples_new/microservices/client/dist/index.html b/examples_new/microservices/client/dist/index.html new file mode 100644 index 000000000..ead84e7dc --- /dev/null +++ b/examples_new/microservices/client/dist/index.html @@ -0,0 +1,20 @@ + + + + + + + + + + Chronos Microservices + + + + +
+ +