diff --git a/core/org.eclipse.smila.solr/code/src/org/eclipse/smila/solr/service/SolrOperationServiceImpl.java b/core/org.eclipse.smila.solr/code/src/org/eclipse/smila/solr/service/SolrOperationServiceImpl.java
index acde88a..4729a72 100755
--- a/core/org.eclipse.smila.solr/code/src/org/eclipse/smila/solr/service/SolrOperationServiceImpl.java
+++ b/core/org.eclipse.smila.solr/code/src/org/eclipse/smila/solr/service/SolrOperationServiceImpl.java
@@ -1,118 +1,128 @@
-/**
- *
- */
-package org.eclipse.smila.solr.service;
-
-import java.io.IOException;
-import java.util.List;
-import java.util.Map;
-
-import org.apache.commons.httpclient.HttpClient;
-import org.apache.commons.httpclient.HttpException;
-import org.apache.commons.httpclient.MultiThreadedHttpConnectionManager;
-import org.apache.commons.lang.NotImplementedException;
-import org.apache.commons.logging.Log;
-import org.apache.commons.logging.LogFactory;
-import org.apache.solr.client.solrj.SolrRequest;
-import org.apache.solr.client.solrj.SolrServerException;
-import org.apache.solr.client.solrj.response.SolrPingResponse;
-import org.apache.solr.common.util.NamedList;
-import org.eclipse.smila.datamodel.Any;
-import org.eclipse.smila.datamodel.util.AnyUtil;
-import org.eclipse.smila.solr.SolrConfig.Mode;
-import org.eclipse.smila.solr.SolrOperationService;
-import org.eclipse.smila.solr.SolrServerService;
-import org.eclipse.smila.solr.SolrUtils;
-import org.eclipse.smila.solr.administration.SchemaRequest;
-import org.eclipse.smila.solr.administration.SmilaCollectionAdminRequest;
-import org.eclipse.smila.solr.administration.SmilaCoreAdminRequest;
-
-/**
- * @author pwissel
- *
- */
-public class SolrOperationServiceImpl implements SolrOperationService {
-
-  private final Log _log = LogFactory.getLog(getClass());
-
-  private final HttpClient _httpClient;
-
-  private SolrServerService _serverService;
-
-  public SolrOperationServiceImpl() {
-    final MultiThreadedHttpConnectionManager manager = new MultiThreadedHttpConnectionManager();
-    _httpClient = new HttpClient(manager);
-  }
-
-  /*
-   * (non-Javadoc)
-   *
-   * @see org.eclipse.smila.solr.SolrOperationService#processAdminOperation(java.lang.String, java.util.Map)
-   */
-  @Override
-  public Any processAdminOperation(String action, Map<String, String[]> params) {
-    try {
-      SolrRequest request = null;
-      final Mode mode = _serverService.getConfig().getMode();
-      switch (mode) {
-        case CLOUD:
-          request = new SmilaCollectionAdminRequest(action, params);
-          break;
-        case EMBEDDED:
-        case HTTP:
-          request = new SmilaCoreAdminRequest(action, params);
-          break;
-        default:
-          final String message = String.format("Unknown mode: %s", mode.toString());
-          throw new UnsupportedOperationException(message);
-      }
-      final NamedList<Object> response = _serverService.getServer().request(request);
-      return SolrUtils.parseNamedList(response);
-    } catch (Exception exception) {
-      return AnyUtil.exceptionToAny(exception);
-    }
-  }
-
-  @Override
-  public Any processPingOperation(final String index) {
-    try {
-      final SolrPingResponse response = _serverService.getServer(index).ping();
-      return SolrUtils.parseNamedList(response.getResponse());
-    } catch (SolrServerException | IOException exception) {
-      return AnyUtil.exceptionToAny(exception);
-    }
-  }
-
-  @Override
-  public Any processSchemaRequest(final String index, final Map<String, String[]> params, final List<String> path)
-    throws HttpException, IOException {
-    final Mode mode = _serverService.getConfig().getMode();
-    switch (mode) {
-      case CLOUD:
-      case HTTP:
-        final String restUri = _serverService.getConfig().getRestUri();
-        final SchemaRequest schemaRequest = new SchemaRequest(_httpClient, restUri);
-        return schemaRequest.getAsAny(index, params, path);
-      default:
-        final String message = String.format("Can not process schema request for mode: %s", mode.toString());
-        throw new NotImplementedException(message);
-    }
-  }
-
-  protected void bindSolrServerService(final SolrServerService serverService) {
-    if (_log.isDebugEnabled()) {
-      _log.debug("Bind SolrServerService...");
-    }
-    _serverService = serverService;
-  }
-
-  protected void unbindSolrServerService(final SolrServerService serverService) {
-    if (_serverService == serverService) {
-      if (_log.isDebugEnabled()) {
-        _log.debug("Unbind SolrServerService...");
-      }
-      _serverService = null;
-    }
-  }
-
-}
+/**
+ *
+ */
+package org.eclipse.smila.solr.service;
+
+import java.io.IOException;
+import java.util.List;
+import java.util.Map;
+
+import org.apache.commons.httpclient.HttpClient;
+import org.apache.commons.httpclient.HttpException;
+import org.apache.commons.httpclient.MultiThreadedHttpConnectionManager;
+import org.apache.commons.lang.NotImplementedException;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.apache.solr.client.solrj.SolrRequest;
+import org.apache.solr.client.solrj.SolrServer;
+import org.apache.solr.client.solrj.SolrServerException;
+import org.apache.solr.client.solrj.request.SolrPing;
+import org.apache.solr.client.solrj.response.SolrPingResponse;
+import org.apache.solr.common.util.NamedList;
+import org.eclipse.smila.datamodel.Any;
+import org.eclipse.smila.datamodel.util.AnyUtil;
+import org.eclipse.smila.solr.SolrConfig.Mode;
+import org.eclipse.smila.solr.SolrOperationService;
+import org.eclipse.smila.solr.SolrServerService;
+import org.eclipse.smila.solr.SolrUtils;
+import org.eclipse.smila.solr.administration.SchemaRequest;
+import org.eclipse.smila.solr.administration.SmilaCollectionAdminRequest;
+import org.eclipse.smila.solr.administration.SmilaCoreAdminRequest;
+
+/**
+ * @author pwissel
+ *
+ */
+public class SolrOperationServiceImpl implements SolrOperationService {
+
+  private final Log _log = LogFactory.getLog(getClass());
+
+  private final HttpClient _httpClient;
+
+  private SolrServerService _serverService;
+
+  public SolrOperationServiceImpl() {
+    final MultiThreadedHttpConnectionManager manager = new MultiThreadedHttpConnectionManager();
+    _httpClient = new HttpClient(manager);
+  }
+
+  /*
+   * (non-Javadoc)
+   *
+   * @see org.eclipse.smila.solr.SolrOperationService#processAdminOperation(java.lang.String, java.util.Map)
+   */
+  @Override
+  public Any processAdminOperation(String action, Map<String, String[]> params) {
+    try {
+      SolrRequest request = null;
+      final Mode mode = _serverService.getConfig().getMode();
+      switch (mode) {
+        case CLOUD:
+          request = new SmilaCollectionAdminRequest(action, params);
+          break;
+        case EMBEDDED:
+        case HTTP:
+          request = new SmilaCoreAdminRequest(action, params);
+          break;
+        default:
+          final String message = String.format("Unknown mode: %s", mode.toString());
+          throw new UnsupportedOperationException(message);
+      }
+      final NamedList<Object> response = _serverService.getServer().request(request);
+      return SolrUtils.parseNamedList(response);
+    } catch (Exception exception) {
+      return AnyUtil.exceptionToAny(exception);
+    }
+  }
+
+  @Override
+  public Any processPingOperation(final String index) {
+    try {
+      // get server
+      final SolrServer server = _serverService.getServer(index);
+      // create ping request
+      final SolrPing ping = new SolrPing();
+      ping.getParams().add("distrib", "true");
+      // process request on server
+      final SolrPingResponse pingResponse = ping.process(server);
+      // parse server response
+      final NamedList<Object> response = pingResponse.getResponse();
+      return SolrUtils.parseNamedList(response);
+    } catch (SolrServerException | IOException exception) {
+      return AnyUtil.exceptionToAny(exception);
+    }
+  }
+
+  @Override
+  public Any processSchemaRequest(final String index, final Map<String, String[]> params, final List<String> path)
+    throws HttpException, IOException {
+    final Mode mode = _serverService.getConfig().getMode();
+    switch (mode) {
+      case CLOUD:
+      case HTTP:
+        final String restUri = _serverService.getConfig().getRestUri();
+        final SchemaRequest schemaRequest = new SchemaRequest(_httpClient, restUri);
+        return schemaRequest.getAsAny(index, params, path);
+      default:
+        final String message = String.format("Can not process schema request for mode: %s", mode.toString());
+        throw new NotImplementedException(message);
+    }
+  }
+
+  protected void bindSolrServerService(final SolrServerService serverService) {
+    if (_log.isDebugEnabled()) {
+      _log.debug("Bind SolrServerService...");
+    }
+    _serverService = serverService;
+  }
+
+  protected void unbindSolrServerService(final SolrServerService serverService) {
+    if (_serverService == serverService) {
+      if (_log.isDebugEnabled()) {
+        _log.debug("Unbind SolrServerService...");
+      }
+      _serverService = null;
+    }
+  }
+
+}
