001/** 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to You under the Apache License, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017package org.apache.camel.component.log; 018 019import org.apache.camel.Component; 020import org.apache.camel.LoggingLevel; 021import org.apache.camel.Processor; 022import org.apache.camel.Producer; 023import org.apache.camel.impl.ProcessorEndpoint; 024import org.apache.camel.processor.CamelLogProcessor; 025import org.apache.camel.processor.DefaultExchangeFormatter; 026import org.apache.camel.processor.ThroughputLogger; 027import org.apache.camel.spi.ExchangeFormatter; 028import org.apache.camel.spi.Metadata; 029import org.apache.camel.spi.UriEndpoint; 030import org.apache.camel.spi.UriParam; 031import org.apache.camel.spi.UriPath; 032import org.apache.camel.util.CamelLogger; 033import org.apache.camel.util.ServiceHelper; 034import org.slf4j.Logger; 035 036/** 037 * The log component logs message exchanges to the underlying logging mechanism. 038 * 039 * Camel uses sfl4j which allows you to configure logging to the actual logging system. 040 */ 041@UriEndpoint(scheme = "log", title = "Log", syntax = "log:loggerName", producerOnly = true, label = "core,monitoring") 042public class LogEndpoint extends ProcessorEndpoint { 043 044 private volatile Processor logger; 045 private Logger providedLogger; 046 private ExchangeFormatter localFormatter; 047 048 @UriPath(description = "Name of the logging category to use") @Metadata(required = "true") 049 private String loggerName; 050 @UriParam(defaultValue = "INFO", enums = "ERROR,WARN,INFO,DEBUG,TRACE,OFF") 051 private String level; 052 @UriParam 053 private String marker; 054 @UriParam 055 private Integer groupSize; 056 @UriParam 057 private Long groupInterval; 058 @UriParam(defaultValue = "true") 059 private Boolean groupActiveOnly; 060 @UriParam 061 private Long groupDelay; 062 // we want to include the uri options of the DefaultExchangeFormatter 063 @UriParam 064 private DefaultExchangeFormatter exchangeFormatter; 065 066 public LogEndpoint() { 067 } 068 069 public LogEndpoint(String endpointUri, Component component) { 070 super(endpointUri, component); 071 } 072 073 public LogEndpoint(String endpointUri, Component component, Processor logger) { 074 super(endpointUri, component); 075 setLogger(logger); 076 } 077 078 @Override 079 protected void doStart() throws Exception { 080 if (logger == null) { 081 // setup a new logger here 082 CamelLogger camelLogger; 083 LoggingLevel loggingLevel = LoggingLevel.INFO; 084 if (level != null) { 085 loggingLevel = LoggingLevel.valueOf(level); 086 } 087 if (providedLogger == null) { 088 camelLogger = new CamelLogger(loggerName, loggingLevel, getMarker()); 089 } else { 090 camelLogger = new CamelLogger(providedLogger, loggingLevel, getMarker()); 091 } 092 if (getGroupSize() != null) { 093 logger = new ThroughputLogger(camelLogger, getGroupSize()); 094 } else if (getGroupInterval() != null) { 095 Boolean groupActiveOnly = getGroupActiveOnly() != null ? getGroupActiveOnly() : Boolean.TRUE; 096 Long groupDelay = getGroupDelay(); 097 logger = new ThroughputLogger(camelLogger, this.getCamelContext(), getGroupInterval(), groupDelay, groupActiveOnly); 098 } else { 099 logger = new CamelLogProcessor(camelLogger, localFormatter); 100 } 101 // the logger is the processor 102 setProcessor(this.logger); 103 } 104 ServiceHelper.startService(logger); 105 } 106 107 @Override 108 protected void doStop() throws Exception { 109 ServiceHelper.stopService(logger); 110 } 111 112 public void setLogger(Processor logger) { 113 this.logger = logger; 114 // the logger is the processor 115 setProcessor(this.logger); 116 } 117 118 public Processor getLogger() { 119 return logger; 120 } 121 122 @Override 123 public Producer createProducer() throws Exception { 124 return new LogProducer(this, this.logger); 125 } 126 127 @Override 128 protected String createEndpointUri() { 129 return "log:" + logger.toString(); 130 } 131 132 /** 133 * Logging level to use. 134 * <p/> 135 * The default value is INFO. 136 */ 137 public String getLevel() { 138 return level; 139 } 140 141 /** 142 * Logging level to use. 143 * <p/> 144 * The default value is INFO. 145 */ 146 public void setLevel(String level) { 147 this.level = level; 148 } 149 150 /** 151 * An optional Marker name to use. 152 */ 153 public String getMarker() { 154 return marker; 155 } 156 157 /** 158 * An optional Marker name to use. 159 */ 160 public void setMarker(String marker) { 161 this.marker = marker; 162 } 163 164 /** 165 * An integer that specifies a group size for throughput logging. 166 */ 167 public Integer getGroupSize() { 168 return groupSize; 169 } 170 171 /** 172 * An integer that specifies a group size for throughput logging. 173 */ 174 public void setGroupSize(Integer groupSize) { 175 this.groupSize = groupSize; 176 } 177 178 /** 179 * If specified will group message stats by this time interval (in millis) 180 */ 181 public Long getGroupInterval() { 182 return groupInterval; 183 } 184 185 /** 186 * If specified will group message stats by this time interval (in millis) 187 */ 188 public void setGroupInterval(Long groupInterval) { 189 this.groupInterval = groupInterval; 190 } 191 192 /** 193 * If true, will hide stats when no new messages have been received for a time interval, if false, show stats regardless of message traffic. 194 */ 195 public Boolean getGroupActiveOnly() { 196 return groupActiveOnly; 197 } 198 199 /** 200 * If true, will hide stats when no new messages have been received for a time interval, if false, show stats regardless of message traffic. 201 */ 202 public void setGroupActiveOnly(Boolean groupActiveOnly) { 203 this.groupActiveOnly = groupActiveOnly; 204 } 205 206 /** 207 * Set the initial delay for stats (in millis) 208 */ 209 public Long getGroupDelay() { 210 return groupDelay; 211 } 212 213 /** 214 * Set the initial delay for stats (in millis) 215 */ 216 public void setGroupDelay(Long groupDelay) { 217 this.groupDelay = groupDelay; 218 } 219 220 public ExchangeFormatter getLocalFormatter() { 221 return localFormatter; 222 } 223 224 public void setLocalFormatter(ExchangeFormatter localFormatter) { 225 this.localFormatter = localFormatter; 226 } 227 228 public Logger getProvidedLogger() { 229 return providedLogger; 230 } 231 232 public void setProvidedLogger(Logger providedLogger) { 233 this.providedLogger = providedLogger; 234 } 235 236 /** 237 * The logger name to use 238 */ 239 public String getLoggerName() { 240 return loggerName; 241 } 242 243 /** 244 * The logger name to use 245 */ 246 public void setLoggerName(String loggerName) { 247 this.loggerName = loggerName; 248 } 249}