├── .github └── workflows │ └── build.yml ├── .gitignore ├── .rubocop.yml ├── Gemfile ├── LICENSE.txt ├── README.md ├── Rakefile ├── bin ├── console └── setup ├── colorize_logs.gemspec ├── lib ├── colorize_logs.rb └── colorize_logs │ ├── formatter.rb │ └── version.rb └── test ├── test_colorize_logs.rb └── test_helper.rb /.github/workflows/build.yml: -------------------------------------------------------------------------------- 1 | # This workflow uses actions that are not certified by GitHub. 2 | # They are provided by a third-party and are governed by 3 | # separate terms of service, privacy policy, and support 4 | # documentation. 5 | # This workflow will download a prebuilt Ruby version, install dependencies and run tests with Rake 6 | # For more information see: https://github.com/marketplace/actions/setup-ruby-jruby-and-truffleruby 7 | 8 | name: build 9 | 10 | on: 11 | push: 12 | branches: [ "main" ] 13 | pull_request: 14 | branches: [ "main" ] 15 | 16 | permissions: 17 | contents: read 18 | 19 | jobs: 20 | test: 21 | 22 | runs-on: ubuntu-latest 23 | strategy: 24 | matrix: 25 | ruby-version: ['2.6', '2.7', '3.0'] 26 | 27 | steps: 28 | - uses: actions/checkout@v3 29 | - name: Set up Ruby 30 | # To automatically get bug fixes and new Ruby versions for ruby/setup-ruby, 31 | # change this to (see https://github.com/ruby/setup-ruby#versioning): 32 | # uses: ruby/setup-ruby@v1 33 | uses: ruby/setup-ruby@55283cc23133118229fd3f97f9336ee23a179fcf # v1.146.0 34 | with: 35 | ruby-version: ${{ matrix.ruby-version }} 36 | bundler-cache: true # runs 'bundle install' and caches installed gems automatically 37 | - name: Run tests 38 | run: bundle exec rake 39 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | /.bundle/ 2 | /.yardoc 3 | /_yardoc/ 4 | /coverage/ 5 | /doc/ 6 | /pkg/ 7 | /spec/reports/ 8 | /tmp/ 9 | *.lock 10 | -------------------------------------------------------------------------------- /.rubocop.yml: -------------------------------------------------------------------------------- 1 | AllCops: 2 | TargetRubyVersion: 2.6 3 | 4 | Style/StringLiterals: 5 | Enabled: true 6 | EnforcedStyle: double_quotes 7 | 8 | Style/StringLiteralsInInterpolation: 9 | Enabled: true 10 | EnforcedStyle: double_quotes 11 | 12 | Layout/LineLength: 13 | Max: 120 14 | -------------------------------------------------------------------------------- /Gemfile: -------------------------------------------------------------------------------- 1 | # frozen_string_literal: true 2 | 3 | source "https://rubygems.org" 4 | 5 | # Specify your gem's dependencies in colorize_logs.gemspec 6 | gemspec 7 | 8 | gem "rake", "~> 13.0" 9 | 10 | gem "minitest", "~> 5.0" 11 | 12 | gem "rubocop", "~> 1.21" 13 | 14 | gem "activesupport" 15 | 16 | gem "colorize" 17 | 18 | group :test do 19 | gem "mocha" 20 | end 21 | -------------------------------------------------------------------------------- /LICENSE.txt: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2023 Santosh Wadghule 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # ColorizeLogs 2 | 3 | As developers, we often deal with current controller's action, its main view page and the layout associated with it. To 4 | trace and debug these logs information, we check the logs through our console. 5 | 6 | However, by default, the logs are all in the same color, which makes it difficult to find the ones which we're working 7 | on. To simplify our lives and speed up the debugging process, we want to assign different colors to these logs. 8 | This will make it much easier for us to spot the right information and save time when we're fixing issues and improving 9 | our software. 10 | 11 | To ease our development time, we can use this gem. It will colorize the logs for controller's action, view, layout, 12 | and etc. 13 | 14 | ![colorize_logs](https://user-images.githubusercontent.com/77895/270565495-a75fc46d-b574-4fbe-9976-998abbf0b7b7.png) 15 | 16 | [![Build Status](https://github.com/mechanicles/colorize_logs/actions/workflows/build.yml/badge.svg?branch=main)](https://github.com/mechanicles/colorize_logs/actions) 17 | 18 | ## Installation 19 | 20 | Add this line to your application’s Gemfile: 21 | 22 | ```ruby 23 | gem "colorize_logs" 24 | ``` 25 | 26 | If bundler is not being used to manage dependencies, install the gem by executing: 27 | 28 | $ gem install colorize_logs 29 | 30 | ## Usage 31 | 32 | Create an initializer file `config/initializers/colorize_logs.rb` and add the following code: 33 | 34 | ```ruby 35 | # frozen_string_literal: true 36 | 37 | colorize_logs_formatter = ColorizeLogs::Formatter.new 38 | 39 | colorize_logs_formatter.configure do 40 | match(/Processing by/) do |msg| 41 | msg.red 42 | end 43 | 44 | match(/Rendering layout/) do |msg| 45 | msg.green 46 | end 47 | 48 | match(/Rendering.*within layouts/) do |msg| 49 | msg.green 50 | end 51 | end 52 | 53 | ::Rails.logger.formatter = colorize_logs_formatter 54 | ``` 55 | 56 | That's it. Restart your server and you should see the logs in different colors. 57 | 58 | 59 | ## Credits 60 | 61 | This gem is inspired by [Shog](https://github.com/phallguy/shog) gem. All the credits goes to the author of Shog gem. 62 | I had to create this one as original gem is not maintained anymore and I wanted minimal stuff from it. 63 | 64 | ## Development 65 | 66 | After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake test` to run the tests. You can 67 | also run `bin/console` for an interactive prompt that will allow you to experiment. 68 | 69 | To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the 70 | version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, 71 | push git commits and the created tag, and push the `.gem` file to [rubygems.org](https://rubygems.org). 72 | 73 | ## Contributing 74 | 75 | Bug reports and pull requests are welcome on GitHub at https://github.com/mechanicles/colorize_logs. This project is 76 | intended to be a safe, welcoming space for collaboration, and contributors are expected to adhere to the 77 | [code of conduct](https://github.com/mechanicles/colorize_logs/blob/master/CODE_OF_CONDUCT.md). 78 | 79 | ## License 80 | 81 | The gem is available as open source under the terms of the [MIT License](https://opensource.org/licenses/MIT). -------------------------------------------------------------------------------- /Rakefile: -------------------------------------------------------------------------------- 1 | # frozen_string_literal: true 2 | 3 | require "bundler/gem_tasks" 4 | require "rake/testtask" 5 | 6 | Rake::TestTask.new(:test) do |t| 7 | t.libs << "test" 8 | t.libs << "lib" 9 | t.test_files = FileList["test/**/test_*.rb"] 10 | end 11 | 12 | require "rubocop/rake_task" 13 | 14 | RuboCop::RakeTask.new 15 | 16 | task default: %i[test rubocop] 17 | -------------------------------------------------------------------------------- /bin/console: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env ruby 2 | # frozen_string_literal: true 3 | 4 | require "bundler/setup" 5 | require "colorize_logs" 6 | 7 | # You can add fixtures and/or initialization code here to make experimenting 8 | # with your gem easier. You can also use a different console, if you like. 9 | 10 | require "irb" 11 | IRB.start(__FILE__) 12 | -------------------------------------------------------------------------------- /bin/setup: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | set -euo pipefail 3 | IFS=$'\n\t' 4 | set -vx 5 | 6 | bundle install 7 | 8 | # Do any other automated setup that you need to do here 9 | -------------------------------------------------------------------------------- /colorize_logs.gemspec: -------------------------------------------------------------------------------- 1 | # frozen_string_literal: true 2 | 3 | require_relative "lib/colorize_logs/version" 4 | 5 | Gem::Specification.new do |spec| 6 | spec.name = "colorize_logs" 7 | spec.version = ColorizeLogs::VERSION 8 | spec.summary = "Colorize your Rails logs" 9 | spec.homepage = "https://github.com/mechanicles/colorize_logs" 10 | spec.license = "MIT" 11 | 12 | spec.authors = ["Santosh Wadghule"] 13 | spec.email = ["santosh.wadghule@gmail.com"] 14 | 15 | spec.required_ruby_version = ">= 2.6.0" 16 | 17 | spec.files = Dir["*.{md,txt}", "{lib}/**/*"] 18 | spec.require_paths = ["lib"] 19 | 20 | # Uncomment to register a new dependency of your gem 21 | spec.add_dependency "activesupport" 22 | spec.add_dependency "colorize" 23 | end 24 | -------------------------------------------------------------------------------- /lib/colorize_logs.rb: -------------------------------------------------------------------------------- 1 | # frozen_string_literal: true 2 | 3 | require_relative "colorize_logs/version" 4 | require_relative "colorize_logs/formatter" 5 | 6 | module ColorizeLogs 7 | class Error < StandardError; end 8 | end 9 | -------------------------------------------------------------------------------- /lib/colorize_logs/formatter.rb: -------------------------------------------------------------------------------- 1 | # frozen_string_literal: true 2 | 3 | require "active_support/tagged_logging" 4 | require "colorize" 5 | 6 | module ColorizeLogs 7 | # Custom formatter for Rails logger 8 | class Formatter < ActiveSupport::Logger::SimpleFormatter 9 | include ActiveSupport::TaggedLogging::Formatter 10 | 11 | def initialize 12 | super 13 | 14 | @matchers = {} 15 | end 16 | 17 | def configure(&block) 18 | instance_eval(&block) 19 | self 20 | end 21 | 22 | def call(severity, time, progname, msg) 23 | return if msg.blank? 24 | 25 | msg = colorize_message(msg) 26 | 27 | super(severity, time, progname, msg) 28 | end 29 | 30 | private 31 | 32 | def colorize_message(msg) 33 | msg = msg.is_a?(String) ? msg : msg.inspect 34 | 35 | proc = find_matching_pattern(msg) 36 | 37 | proc ? proc.call(msg) : msg 38 | end 39 | 40 | def find_matching_pattern(msg) 41 | matcher = @matchers.find { |pattern, _| pattern.match(msg) } 42 | 43 | matcher&.last 44 | end 45 | 46 | def match(pattern, proc = nil, &block) 47 | proc ||= block 48 | @matchers[pattern] = proc 49 | self 50 | end 51 | end 52 | end 53 | -------------------------------------------------------------------------------- /lib/colorize_logs/version.rb: -------------------------------------------------------------------------------- 1 | # frozen_string_literal: true 2 | 3 | module ColorizeLogs 4 | VERSION = "0.1.0" 5 | end 6 | -------------------------------------------------------------------------------- /test/test_colorize_logs.rb: -------------------------------------------------------------------------------- 1 | # frozen_string_literal: true 2 | 3 | require "test_helper" 4 | 5 | class TestColorizeLogs < Minitest::Test 6 | def test_log_message_becomes_red 7 | String.any_instance.expects(:red).once 8 | 9 | formatter.call("INFO", Time.now, "test", "Processing by") 10 | end 11 | 12 | def test_log_message_becomes_green 13 | String.any_instance.expects(:green).once 14 | 15 | formatter.call("INFO", Time.now, "test", "Rendering layout") 16 | end 17 | 18 | def test_log_message_becomes_blue 19 | String.any_instance.expects(:blue).once 20 | 21 | formatter.call("INFO", Time.now, "test", "Rendering some view page within layouts") 22 | end 23 | 24 | def test_log_message_fails_to_become_blue 25 | String.any_instance.expects(:blue).never 26 | 27 | formatter.call("INFO", Time.now, "test", "some other message") 28 | end 29 | 30 | def formatter 31 | colorize_logs_formatter = ::ColorizeLogs::Formatter.new 32 | 33 | colorize_logs_formatter.configure do 34 | match(/Processing by/, &:red) 35 | 36 | match(/Rendering layout/, &:green) 37 | 38 | match(/Rendering.*within layouts/, &:blue) 39 | end 40 | end 41 | end 42 | -------------------------------------------------------------------------------- /test/test_helper.rb: -------------------------------------------------------------------------------- 1 | # frozen_string_literal: true 2 | 3 | $LOAD_PATH.unshift File.expand_path("../lib", __dir__) 4 | require "colorize_logs" 5 | 6 | require "minitest/autorun" 7 | require "active_support" 8 | require "mocha/minitest" 9 | --------------------------------------------------------------------------------