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.logging.log4j.core.filter; 018 019import java.util.Arrays; 020import java.util.Iterator; 021import java.util.List; 022 023import org.apache.logging.log4j.Level; 024import org.apache.logging.log4j.Marker; 025import org.apache.logging.log4j.core.AbstractLifeCycle; 026import org.apache.logging.log4j.core.Filter; 027import org.apache.logging.log4j.core.LogEvent; 028import org.apache.logging.log4j.core.Logger; 029import org.apache.logging.log4j.core.config.Node; 030import org.apache.logging.log4j.core.config.plugins.Plugin; 031import org.apache.logging.log4j.core.config.plugins.PluginElement; 032import org.apache.logging.log4j.core.config.plugins.PluginFactory; 033import org.apache.logging.log4j.core.util.ObjectArrayIterator; 034import org.apache.logging.log4j.message.Message; 035 036/** 037 * Composes and invokes one or more filters. 038 */ 039@Plugin(name = "filters", category = Node.CATEGORY, printObject = true) 040public final class CompositeFilter extends AbstractLifeCycle implements Iterable<Filter>, Filter { 041 042 private static final Filter[] EMPTY_FILTERS = new Filter[0]; 043 private final Filter[] filters; 044 045 private CompositeFilter() { 046 this.filters = EMPTY_FILTERS; 047 } 048 049 private CompositeFilter(final Filter[] filters) { 050 this.filters = filters == null ? EMPTY_FILTERS : filters; 051 } 052 053 public CompositeFilter addFilter(final Filter filter) { 054 if (filter == null) { 055 // null does nothing 056 return this; 057 } 058 final Filter[] copy = Arrays.copyOf(this.filters, this.filters.length + 1); 059 copy[this.filters.length] = filter; 060 return new CompositeFilter(copy); 061 } 062 063 public CompositeFilter removeFilter(final Filter filter) { 064 if (filter == null) { 065 // null does nothing 066 return this; 067 } 068 // This is not a great implementation but simpler than copying Apache Commons 069 // Lang ArrayUtils.removeElement() and associated bits (MutableInt), 070 // which is OK since removing a filter should not be on the critical path. 071 final List<Filter> filterList = Arrays.asList(this.filters); 072 filterList.remove(filter); 073 return new CompositeFilter(filterList.toArray(new Filter[this.filters.length - 1])); 074 } 075 076 @Override 077 public Iterator<Filter> iterator() { 078 return new ObjectArrayIterator<>(filters); 079 } 080 081 /** 082 * Gets a new list over the internal filter array. 083 * 084 * @return a new list over the internal filter array 085 * @deprecated Use {@link #getFiltersArray()} 086 */ 087 @Deprecated 088 public List<Filter> getFilters() { 089 return Arrays.asList(filters); 090 } 091 092 public Filter[] getFiltersArray() { 093 return filters; 094 } 095 096 /** 097 * Returns whether this composite contains any filters. 098 * 099 * @return whether this composite contains any filters. 100 */ 101 public boolean isEmpty() { 102 return this.filters.length == 0; 103 } 104 105 public int size() { 106 return filters.length; 107 } 108 109 @Override 110 public void start() { 111 this.setStarting(); 112 for (final Filter filter : filters) { 113 filter.start(); 114 } 115 this.setStarted(); 116 } 117 118 @Override 119 public void stop() { 120 this.setStopping(); 121 for (final Filter filter : filters) { 122 filter.stop(); 123 } 124 this.setStopped(); 125 } 126 127 /** 128 * Returns the result that should be returned when the filter does not match the event. 129 * 130 * @return the Result that should be returned when the filter does not match the event. 131 */ 132 @Override 133 public Result getOnMismatch() { 134 return Result.NEUTRAL; 135 } 136 137 /** 138 * Returns the result that should be returned when the filter matches the event. 139 * 140 * @return the Result that should be returned when the filter matches the event. 141 */ 142 @Override 143 public Result getOnMatch() { 144 return Result.NEUTRAL; 145 } 146 147 /** 148 * Filter an event. 149 * 150 * @param logger 151 * The Logger. 152 * @param level 153 * The event logging Level. 154 * @param marker 155 * The Marker for the event or null. 156 * @param msg 157 * String text to filter on. 158 * @param params 159 * An array of parameters or null. 160 * @return the Result. 161 */ 162 @Override 163 public Result filter(final Logger logger, final Level level, final Marker marker, final String msg, 164 final Object... params) { 165 Result result = Result.NEUTRAL; 166 for (int i = 0; i < filters.length; i++) { 167 result = filters[i].filter(logger, level, marker, msg, params); 168 if (result == Result.ACCEPT || result == Result.DENY) { 169 return result; 170 } 171 } 172 return result; 173 } 174 175 /** 176 * Filter an event. 177 * 178 * @param logger 179 * The Logger. 180 * @param level 181 * The event logging Level. 182 * @param marker 183 * The Marker for the event or null. 184 * @param msg 185 * String text to filter on. 186 * @param p0 the message parameters 187 * @return the Result. 188 */ 189 @Override 190 public Result filter(final Logger logger, final Level level, final Marker marker, final String msg, 191 final Object p0) { 192 Result result = Result.NEUTRAL; 193 for (int i = 0; i < filters.length; i++) { 194 result = filters[i].filter(logger, level, marker, msg, p0); 195 if (result == Result.ACCEPT || result == Result.DENY) { 196 return result; 197 } 198 } 199 return result; 200 } 201 202 /** 203 * Filter an event. 204 * 205 * @param logger 206 * The Logger. 207 * @param level 208 * The event logging Level. 209 * @param marker 210 * The Marker for the event or null. 211 * @param msg 212 * String text to filter on. 213 * @param p0 the message parameters 214 * @param p1 the message parameters 215 * @return the Result. 216 */ 217 @Override 218 public Result filter(final Logger logger, final Level level, final Marker marker, final String msg, 219 final Object p0, final Object p1) { 220 Result result = Result.NEUTRAL; 221 for (int i = 0; i < filters.length; i++) { 222 result = filters[i].filter(logger, level, marker, msg, p0, p1); 223 if (result == Result.ACCEPT || result == Result.DENY) { 224 return result; 225 } 226 } 227 return result; 228 } 229 230 /** 231 * Filter an event. 232 * 233 * @param logger 234 * The Logger. 235 * @param level 236 * The event logging Level. 237 * @param marker 238 * The Marker for the event or null. 239 * @param msg 240 * String text to filter on. 241 * @param p0 the message parameters 242 * @param p1 the message parameters 243 * @param p2 the message parameters 244 * @return the Result. 245 */ 246 @Override 247 public Result filter(final Logger logger, final Level level, final Marker marker, final String msg, 248 final Object p0, final Object p1, final Object p2) { 249 Result result = Result.NEUTRAL; 250 for (int i = 0; i < filters.length; i++) { 251 result = filters[i].filter(logger, level, marker, msg, p0, p1, p2); 252 if (result == Result.ACCEPT || result == Result.DENY) { 253 return result; 254 } 255 } 256 return result; 257 } 258 259 /** 260 * Filter an event. 261 * 262 * @param logger 263 * The Logger. 264 * @param level 265 * The event logging Level. 266 * @param marker 267 * The Marker for the event or null. 268 * @param msg 269 * String text to filter on. 270 * @param p0 the message parameters 271 * @param p1 the message parameters 272 * @param p2 the message parameters 273 * @param p3 the message parameters 274 * @return the Result. 275 */ 276 @Override 277 public Result filter(final Logger logger, final Level level, final Marker marker, final String msg, 278 final Object p0, final Object p1, final Object p2, final Object p3) { 279 Result result = Result.NEUTRAL; 280 for (int i = 0; i < filters.length; i++) { 281 result = filters[i].filter(logger, level, marker, msg, p0, p1, p2, p3); 282 if (result == Result.ACCEPT || result == Result.DENY) { 283 return result; 284 } 285 } 286 return result; 287 } 288 289 /** 290 * Filter an event. 291 * 292 * @param logger 293 * The Logger. 294 * @param level 295 * The event logging Level. 296 * @param marker 297 * The Marker for the event or null. 298 * @param msg 299 * String text to filter on. 300 * @param p0 the message parameters 301 * @param p1 the message parameters 302 * @param p2 the message parameters 303 * @param p3 the message parameters 304 * @param p4 the message parameters 305 * @return the Result. 306 */ 307 @Override 308 public Result filter(final Logger logger, final Level level, final Marker marker, final String msg, 309 final Object p0, final Object p1, final Object p2, final Object p3, 310 final Object p4) { 311 Result result = Result.NEUTRAL; 312 for (int i = 0; i < filters.length; i++) { 313 result = filters[i].filter(logger, level, marker, msg, p0, p1, p2, p3, p4); 314 if (result == Result.ACCEPT || result == Result.DENY) { 315 return result; 316 } 317 } 318 return result; 319 } 320 321 /** 322 * Filter an event. 323 * 324 * @param logger 325 * The Logger. 326 * @param level 327 * The event logging Level. 328 * @param marker 329 * The Marker for the event or null. 330 * @param msg 331 * String text to filter on. 332 * @param p0 the message parameters 333 * @param p1 the message parameters 334 * @param p2 the message parameters 335 * @param p3 the message parameters 336 * @param p4 the message parameters 337 * @param p5 the message parameters 338 * @return the Result. 339 */ 340 @Override 341 public Result filter(final Logger logger, final Level level, final Marker marker, final String msg, 342 final Object p0, final Object p1, final Object p2, final Object p3, 343 final Object p4, final Object p5) { 344 Result result = Result.NEUTRAL; 345 for (int i = 0; i < filters.length; i++) { 346 result = filters[i].filter(logger, level, marker, msg, p0, p1, p2, p3, p4, p5); 347 if (result == Result.ACCEPT || result == Result.DENY) { 348 return result; 349 } 350 } 351 return result; 352 } 353 354 /** 355 * Filter an event. 356 * 357 * @param logger 358 * The Logger. 359 * @param level 360 * The event logging Level. 361 * @param marker 362 * The Marker for the event or null. 363 * @param msg 364 * String text to filter on. 365 * @param p0 the message parameters 366 * @param p1 the message parameters 367 * @param p2 the message parameters 368 * @param p3 the message parameters 369 * @param p4 the message parameters 370 * @param p5 the message parameters 371 * @param p6 the message parameters 372 * @return the Result. 373 */ 374 @Override 375 public Result filter(final Logger logger, final Level level, final Marker marker, final String msg, 376 final Object p0, final Object p1, final Object p2, final Object p3, 377 final Object p4, final Object p5, final Object p6) { 378 Result result = Result.NEUTRAL; 379 for (int i = 0; i < filters.length; i++) { 380 result = filters[i].filter(logger, level, marker, msg, p0, p1, p2, p3, p4, p5, p6); 381 if (result == Result.ACCEPT || result == Result.DENY) { 382 return result; 383 } 384 } 385 return result; 386 } 387 388 /** 389 * Filter an event. 390 * 391 * @param logger 392 * The Logger. 393 * @param level 394 * The event logging Level. 395 * @param marker 396 * The Marker for the event or null. 397 * @param msg 398 * String text to filter on. 399 * @param p0 the message parameters 400 * @param p1 the message parameters 401 * @param p2 the message parameters 402 * @param p3 the message parameters 403 * @param p4 the message parameters 404 * @param p5 the message parameters 405 * @param p6 the message parameters 406 * @param p7 the message parameters 407 * @return the Result. 408 */ 409 @Override 410 public Result filter(final Logger logger, final Level level, final Marker marker, final String msg, 411 final Object p0, final Object p1, final Object p2, final Object p3, 412 final Object p4, final Object p5, final Object p6, 413 final Object p7) { 414 Result result = Result.NEUTRAL; 415 for (int i = 0; i < filters.length; i++) { 416 result = filters[i].filter(logger, level, marker, msg, p0, p1, p2, p3, p4, p5, p6, p7); 417 if (result == Result.ACCEPT || result == Result.DENY) { 418 return result; 419 } 420 } 421 return result; 422 } 423 424 /** 425 * Filter an event. 426 * 427 * @param logger 428 * The Logger. 429 * @param level 430 * The event logging Level. 431 * @param marker 432 * The Marker for the event or null. 433 * @param msg 434 * String text to filter on. 435 * @param p0 the message parameters 436 * @param p1 the message parameters 437 * @param p2 the message parameters 438 * @param p3 the message parameters 439 * @param p4 the message parameters 440 * @param p5 the message parameters 441 * @param p6 the message parameters 442 * @param p7 the message parameters 443 * @param p8 the message parameters 444 * @return the Result. 445 */ 446 @Override 447 public Result filter(final Logger logger, final Level level, final Marker marker, final String msg, 448 final Object p0, final Object p1, final Object p2, final Object p3, 449 final Object p4, final Object p5, final Object p6, 450 final Object p7, final Object p8) { 451 Result result = Result.NEUTRAL; 452 for (int i = 0; i < filters.length; i++) { 453 result = filters[i].filter(logger, level, marker, msg, p0, p1, p2, p3, p4, p5, p6, p7, p8); 454 if (result == Result.ACCEPT || result == Result.DENY) { 455 return result; 456 } 457 } 458 return result; 459 } 460 461 /** 462 * Filter an event. 463 * 464 * @param logger 465 * The Logger. 466 * @param level 467 * The event logging Level. 468 * @param marker 469 * The Marker for the event or null. 470 * @param msg 471 * String text to filter on. 472 * @param p0 the message parameters 473 * @param p1 the message parameters 474 * @param p2 the message parameters 475 * @param p3 the message parameters 476 * @param p4 the message parameters 477 * @param p5 the message parameters 478 * @param p6 the message parameters 479 * @param p7 the message parameters 480 * @param p8 the message parameters 481 * @param p9 the message parameters 482 * @return the Result. 483 */ 484 @Override 485 public Result filter(final Logger logger, final Level level, final Marker marker, final String msg, 486 final Object p0, final Object p1, final Object p2, final Object p3, 487 final Object p4, final Object p5, final Object p6, 488 final Object p7, final Object p8, final Object p9) { 489 Result result = Result.NEUTRAL; 490 for (int i = 0; i < filters.length; i++) { 491 result = filters[i].filter(logger, level, marker, msg, p0, p1, p2, p3, p4, p5, p6, p7, p8, p9); 492 if (result == Result.ACCEPT || result == Result.DENY) { 493 return result; 494 } 495 } 496 return result; 497 } 498 499 /** 500 * Filter an event. 501 * 502 * @param logger 503 * The Logger. 504 * @param level 505 * The event logging Level. 506 * @param marker 507 * The Marker for the event or null. 508 * @param msg 509 * Any Object. 510 * @param t 511 * A Throwable or null. 512 * @return the Result. 513 */ 514 @Override 515 public Result filter(final Logger logger, final Level level, final Marker marker, final Object msg, 516 final Throwable t) { 517 Result result = Result.NEUTRAL; 518 for (int i = 0; i < filters.length; i++) { 519 result = filters[i].filter(logger, level, marker, msg, t); 520 if (result == Result.ACCEPT || result == Result.DENY) { 521 return result; 522 } 523 } 524 return result; 525 } 526 527 /** 528 * Filter an event. 529 * 530 * @param logger 531 * The Logger. 532 * @param level 533 * The event logging Level. 534 * @param marker 535 * The Marker for the event or null. 536 * @param msg 537 * The Message 538 * @param t 539 * A Throwable or null. 540 * @return the Result. 541 */ 542 @Override 543 public Result filter(final Logger logger, final Level level, final Marker marker, final Message msg, 544 final Throwable t) { 545 Result result = Result.NEUTRAL; 546 for (int i = 0; i < filters.length; i++) { 547 result = filters[i].filter(logger, level, marker, msg, t); 548 if (result == Result.ACCEPT || result == Result.DENY) { 549 return result; 550 } 551 } 552 return result; 553 } 554 555 /** 556 * Filter an event. 557 * 558 * @param event 559 * The Event to filter on. 560 * @return the Result. 561 */ 562 @Override 563 public Result filter(final LogEvent event) { 564 Result result = Result.NEUTRAL; 565 for (int i = 0; i < filters.length; i++) { 566 result = filters[i].filter(event); 567 if (result == Result.ACCEPT || result == Result.DENY) { 568 return result; 569 } 570 } 571 return result; 572 } 573 574 @Override 575 public String toString() { 576 final StringBuilder sb = new StringBuilder(); 577 for (int i = 0; i < filters.length; i++) { 578 if (sb.length() == 0) { 579 sb.append('{'); 580 } else { 581 sb.append(", "); 582 } 583 sb.append(filters[i].toString()); 584 } 585 if (sb.length() > 0) { 586 sb.append('}'); 587 } 588 return sb.toString(); 589 } 590 591 /** 592 * Create a CompositeFilter. 593 * 594 * @param filters 595 * An array of Filters to call. 596 * @return The CompositeFilter. 597 */ 598 @PluginFactory 599 public static CompositeFilter createFilters(@PluginElement("Filters") final Filter[] filters) { 600 return new CompositeFilter(filters); 601 } 602 603}