You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@skywalking.apache.org by wu...@apache.org on 2018/09/07 12:57:12 UTC

[incubator-skywalking] branch alarm updated: Support alarm hook.

This is an automated email from the ASF dual-hosted git repository.

wusheng pushed a commit to branch alarm
in repository https://gitbox.apache.org/repos/asf/incubator-skywalking.git


The following commit(s) were added to refs/heads/alarm by this push:
     new d50e606  Support alarm hook.
d50e606 is described below

commit d50e606ae2eb3184b818b175c60b568c674f7560
Author: Wu Sheng <wu...@foxmail.com>
AuthorDate: Fri Sep 7 20:57:01 2018 +0800

    Support alarm hook.
---
 .../optional-plugins/trace-ignore-plugin/pom.xml   |  29 -----
 .../core/alarm/provider/WebhookCallback.java       |  61 +++++++++++
 .../core/alarm/provider/WebhookCallbackTest.java   | 122 +++++++++++++++++++++
 3 files changed, 183 insertions(+), 29 deletions(-)

diff --git a/apm-sniffer/optional-plugins/trace-ignore-plugin/pom.xml b/apm-sniffer/optional-plugins/trace-ignore-plugin/pom.xml
index 7f2701c..ac0fee7 100644
--- a/apm-sniffer/optional-plugins/trace-ignore-plugin/pom.xml
+++ b/apm-sniffer/optional-plugins/trace-ignore-plugin/pom.xml
@@ -30,33 +30,4 @@
 
     <name>apm-trace-ignore-plugin</name>
     <url>http://maven.apache.org</url>
-
-    <build>
-        <plugins>
-            <plugin>
-                <artifactId>maven-antrun-plugin</artifactId>
-                <executions>
-                    <execution>
-                        <phase>package</phase>
-                        <goals>
-                            <goal>run</goal>
-                        </goals>
-                        <configuration combine.self="override">
-                            <tasks>
-                                <taskdef resource="net/sf/antcontrib/antcontrib.properties" classpathref="maven.runtime.classpath" />
-                                <mkdir dir="${optional.plugin.dest.dir}/${project.artifactId}" />
-                                <!-- copy jar -->
-                                <copy file="${project.build.directory}/${project.artifactId}-${project.version}.jar" tofile="${optional.plugin.dest.dir}/${project.artifactId}/${project.artifactId}-${project.version}.jar" overwrite="true" />
-                                <!-- copy config file -->
-                                <copy file="${project.basedir}/${project.name}.config" tofile="${optional.plugin.dest.dir}/${project.name}/${project.name}.config" overwrite="true" />
-                                <!-- copy introduction -->
-                                <copy file="${project.basedir}/README.md" tofile="${optional.plugin.dest.dir}/${project.name}/README.md" overwrite="true" />
-                                <copy file="${project.basedir}/README_CN.md" tofile="${optional.plugin.dest.dir}/${project.name}/README_CN.md" overwrite="true" />
-                            </tasks>
-                        </configuration>
-                    </execution>
-                </executions>
-            </plugin>
-        </plugins>
-    </build>
 </project>
diff --git a/oap-server/server-alarm-plugin/src/main/java/org/apache/skywalking/oap/server/core/alarm/provider/WebhookCallback.java b/oap-server/server-alarm-plugin/src/main/java/org/apache/skywalking/oap/server/core/alarm/provider/WebhookCallback.java
index 7655b42..582bc4f 100644
--- a/oap-server/server-alarm-plugin/src/main/java/org/apache/skywalking/oap/server/core/alarm/provider/WebhookCallback.java
+++ b/oap-server/server-alarm-plugin/src/main/java/org/apache/skywalking/oap/server/core/alarm/provider/WebhookCallback.java
@@ -18,21 +18,82 @@
 
 package org.apache.skywalking.oap.server.core.alarm.provider;
 
+import com.google.gson.Gson;
+import java.io.IOException;
+import java.io.UnsupportedEncodingException;
 import java.util.List;
+import org.apache.http.StatusLine;
+import org.apache.http.client.ClientProtocolException;
+import org.apache.http.client.config.RequestConfig;
+import org.apache.http.client.methods.CloseableHttpResponse;
+import org.apache.http.client.methods.HttpPost;
+import org.apache.http.entity.StringEntity;
+import org.apache.http.impl.client.CloseableHttpClient;
+import org.apache.http.impl.client.HttpClients;
 import org.apache.skywalking.oap.server.core.alarm.AlarmCallback;
 import org.apache.skywalking.oap.server.core.alarm.AlarmMessage;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
 
 /**
  * Use SkyWalking alarm webhook API call a remote endpoints.
+ *
+ * @author wusheng
  */
 public class WebhookCallback implements AlarmCallback {
+    private static final Logger logger = LoggerFactory.getLogger(WebhookCallback.class);
+    private static final int HTTP_CONNECT_TIMEOUT = 1000;
+    private static final int HTTP_CONNECTION_REQUEST_TIMEOUT = 1000;
+    private static final int HTTP_SOCKET_TIMEOUT = 10000;
+
     private List<String> remoteEndpoints;
+    private RequestConfig requestConfig;
+    private Gson gson = new Gson();
 
     public WebhookCallback(List<String> remoteEndpoints) {
         this.remoteEndpoints = remoteEndpoints;
+        requestConfig = RequestConfig.custom()
+            .setConnectTimeout(HTTP_CONNECT_TIMEOUT)
+            .setConnectionRequestTimeout(HTTP_CONNECTION_REQUEST_TIMEOUT)
+            .setSocketTimeout(HTTP_SOCKET_TIMEOUT).build();
     }
 
     @Override public void doAlarm(List<AlarmMessage> alarmMessage) {
+        if (remoteEndpoints.size() == 0) {
+            return;
+        }
+
+        CloseableHttpClient httpClient = HttpClients.custom().build();
+        try {
+            remoteEndpoints.forEach(url -> {
+                HttpPost post = new HttpPost(url);
+                post.setConfig(requestConfig);
+                post.setHeader("Accept", "application/json");
+                post.setHeader("Content-type", "application/json");
 
+                StringEntity entity = null;
+                try {
+                    entity = new StringEntity(gson.toJson(alarmMessage));
+                    post.setEntity(entity);
+                    CloseableHttpResponse httpResponse = httpClient.execute(post);
+                    StatusLine statusLine = httpResponse.getStatusLine();
+                    if (statusLine != null && statusLine.getStatusCode() != 200) {
+                        logger.error("send alarm to " + url + " failure. Response code: " + statusLine.getStatusCode());
+                    }
+                } catch (UnsupportedEncodingException e) {
+                    logger.error("Alarm to JSON error, " + e.getMessage(), e);
+                } catch (ClientProtocolException e) {
+                    logger.error("send alarm to " + url + " failure.", e);
+                } catch (IOException e) {
+                    logger.error("send alarm to " + url + " failure.", e);
+                }
+            });
+        } finally {
+            try {
+                httpClient.close();
+            } catch (IOException e) {
+                logger.error(e.getMessage(), e);
+            }
+        }
     }
 }
diff --git a/oap-server/server-alarm-plugin/src/test/java/org/apache/skywalking/oap/server/core/alarm/provider/WebhookCallbackTest.java b/oap-server/server-alarm-plugin/src/test/java/org/apache/skywalking/oap/server/core/alarm/provider/WebhookCallbackTest.java
new file mode 100644
index 0000000..961acf7
--- /dev/null
+++ b/oap-server/server-alarm-plugin/src/test/java/org/apache/skywalking/oap/server/core/alarm/provider/WebhookCallbackTest.java
@@ -0,0 +1,122 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package org.apache.skywalking.oap.server.core.alarm.provider;
+
+import com.google.gson.Gson;
+import com.google.gson.JsonArray;
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.net.InetSocketAddress;
+import java.util.ArrayList;
+import java.util.List;
+import javax.servlet.Servlet;
+import javax.servlet.ServletConfig;
+import javax.servlet.ServletException;
+import javax.servlet.ServletRequest;
+import javax.servlet.ServletResponse;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+import org.apache.skywalking.oap.server.core.alarm.AlarmMessage;
+import org.eclipse.jetty.server.Server;
+import org.eclipse.jetty.servlet.ServletContextHandler;
+import org.eclipse.jetty.servlet.ServletHolder;
+import org.junit.After;
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.Test;
+
+public class WebhookCallbackTest implements Servlet {
+    private Server server;
+    private volatile boolean isSuccess = false;
+
+    @Before
+    public void init() throws Exception {
+        server = new Server(new InetSocketAddress("127.0.0.1", 8778));
+        ServletContextHandler servletContextHandler = new ServletContextHandler(ServletContextHandler.NO_SESSIONS);
+        servletContextHandler.setContextPath("/webhook");
+
+        server.setHandler(servletContextHandler);
+
+        ServletHolder servletHolder = new ServletHolder();
+        servletHolder.setServlet(this);
+        servletContextHandler.addServlet(servletHolder, "/receiveAlarm");
+
+        server.start();
+    }
+
+    @After
+    public void stop() throws Exception {
+        server.stop();
+    }
+
+    @Test
+    public void testWebhook() {
+        List<String> remoteEndpoints = new ArrayList<>();
+        remoteEndpoints.add("http://127.0.0.1:8778/webhook/receiveAlarm");
+        WebhookCallback webhookCallback = new WebhookCallback(remoteEndpoints);
+        List<AlarmMessage> alarmMessages = new ArrayList<>(2);
+        alarmMessages.add(new AlarmMessage());
+        alarmMessages.add(new AlarmMessage());
+        webhookCallback.doAlarm(alarmMessages);
+
+        Assert.assertTrue(isSuccess);
+    }
+
+    @Override public void init(ServletConfig config) throws ServletException {
+
+    }
+
+    @Override public ServletConfig getServletConfig() {
+        return null;
+    }
+
+    @Override
+    public void service(ServletRequest request, ServletResponse response) throws ServletException, IOException {
+        HttpServletRequest httpServletRequest = (HttpServletRequest)request;
+        if (httpServletRequest.getContentType().equals("application/json")) {
+            InputStream inputStream = request.getInputStream();
+            ByteArrayOutputStream out = new ByteArrayOutputStream();
+            byte[] buffer = new byte[2048];
+            int readCntOnce;
+
+            while ((readCntOnce = inputStream.read(buffer)) >= 0) {
+                out.write(buffer, 0, readCntOnce);
+            }
+
+            JsonArray elements = new Gson().fromJson(new String(out.toByteArray()), JsonArray.class);
+            if (elements.size() == 2) {
+                ((HttpServletResponse)response).setStatus(200);
+                isSuccess = true;
+                return;
+            }
+
+            ((HttpServletResponse)response).setStatus(500);
+        }
+    }
+
+    @Override public String getServletInfo() {
+        return null;
+    }
+
+    @Override public void destroy() {
+
+    }
+
+}