diff --git a/substrate/client/cli/src/lib.rs b/substrate/client/cli/src/lib.rs
index f16d02cab51d51a77ce8ff535539ad9526ff5b7e..a973acb6f01660ae4db0400c4b7ebd28674fd9af 100644
--- a/substrate/client/cli/src/lib.rs
+++ b/substrate/client/cli/src/lib.rs
@@ -43,7 +43,7 @@ use structopt::{
 	clap::{self, AppSettings},
 	StructOpt,
 };
-use tracing_subscriber::layer::SubscriberExt;
+use tracing_subscriber::{filter::Directive, layer::SubscriberExt};
 
 /// Substrate client CLI
 ///
@@ -234,6 +234,13 @@ pub fn init_logger(
 	tracing_receiver: sc_tracing::TracingReceiver,
 	tracing_targets: Option<String>,
 ) -> std::result::Result<(), String> {
+	fn parse_directives(dirs: impl AsRef<str>) -> Vec<Directive> {
+		dirs.as_ref()
+			.split(',')
+			.filter_map(|s| s.parse().ok())
+			.collect()
+	}
+
 	if let Err(e) = tracing_log::LogTracer::init() {
 		return Err(format!(
 			"Registering Substrate logger failed: {:}!", e
@@ -257,7 +264,7 @@ pub fn init_logger(
 		if lvl != "" {
 			// We're not sure if log or tracing is available at this moment, so silently ignore the
 			// parse error.
-			if let Ok(directive) = lvl.parse() {
+			for directive in parse_directives(lvl) {
 				env_filter = env_filter.add_directive(directive);
 			}
 		}
@@ -266,7 +273,7 @@ pub fn init_logger(
 	if pattern != "" {
 		// We're not sure if log or tracing is available at this moment, so silently ignore the
 		// parse error.
-		if let Ok(directive) = pattern.parse() {
+		for directive in parse_directives(pattern) {
 			env_filter = env_filter.add_directive(directive);
 		}
 	}
@@ -299,3 +306,47 @@ pub fn init_logger(
 	}
 	Ok(())
 }
+
+#[cfg(test)]
+mod tests {
+	use super::*;
+	use tracing::{metadata::Kind, subscriber::Interest, Callsite, Level, Metadata};
+
+	#[test]
+	fn test_logger_filters() {
+		let test_pattern = "afg=debug,sync=trace,client=warn,telemetry";
+		init_logger(&test_pattern, Default::default(), Default::default()).unwrap();
+
+		tracing::dispatcher::get_default(|dispatcher| {
+			let test_filter = |target, level| {
+				struct DummyCallSite;
+				impl Callsite for DummyCallSite {
+					fn set_interest(&self, _: Interest) {}
+					fn metadata(&self) -> &Metadata<'_> {
+						unreachable!();
+					}
+				}
+
+				let metadata = tracing::metadata!(
+					name: "",
+					target: target,
+					level: level,
+					fields: &[],
+					callsite: &DummyCallSite,
+					kind: Kind::SPAN,
+				);
+
+				dispatcher.enabled(&metadata)
+			};
+
+			assert!(test_filter("afg", Level::INFO));
+			assert!(test_filter("afg", Level::DEBUG));
+			assert!(!test_filter("afg", Level::TRACE));
+
+			assert!(test_filter("sync", Level::TRACE));
+			assert!(test_filter("client", Level::WARN));
+
+			assert!(test_filter("telemetry", Level::TRACE));
+		});
+	}
+}