HONEYCOMB-392 - Footprint measuring support 46/8246/7
authorJan Srnicek <jsrnicek@cisco.com>
Tue, 12 Sep 2017 06:22:07 +0000 (08:22 +0200)
committerMarek Gradzki <mgradzki@cisco.com>
Tue, 12 Sep 2017 06:48:17 +0000 (06:48 +0000)
Change-Id: I079c8ceef84cda43159e1823fe42ad77cdc981e8
Signed-off-by: Jan Srnicek <jsrnicek@cisco.com>
14 files changed:
infra/footprint/asciidoc/Readme.adoc [new file with mode: 0644]
infra/footprint/footprint-api/asciidoc/Readme.adoc [new file with mode: 0644]
infra/footprint/footprint-api/pom.xml [new file with mode: 0644]
infra/footprint/footprint-api/src/main/yang/footprint.yang [new file with mode: 0644]
infra/footprint/footprint-impl/asciidoc/Readme.adoc [new file with mode: 0644]
infra/footprint/footprint-impl/pom.xml [new file with mode: 0644]
infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintCustomizer.java [new file with mode: 0644]
infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintModule.java [new file with mode: 0644]
infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintReader.java [new file with mode: 0644]
infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintReaderFactory.java [new file with mode: 0644]
infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintReaderImpl.java [new file with mode: 0644]
infra/footprint/pom.xml [new file with mode: 0644]
infra/minimal-distribution/pom.xml
infra/pom.xml

diff --git a/infra/footprint/asciidoc/Readme.adoc b/infra/footprint/asciidoc/Readme.adoc
new file mode 100644 (file)
index 0000000..a64af09
--- /dev/null
@@ -0,0 +1,3 @@
+= footprint-aggregator
+
+Overview of footprint-aggregator
\ No newline at end of file
diff --git a/infra/footprint/footprint-api/asciidoc/Readme.adoc b/infra/footprint/footprint-api/asciidoc/Readme.adoc
new file mode 100644 (file)
index 0000000..45c8844
--- /dev/null
@@ -0,0 +1,3 @@
+= api
+
+Provides api for reading honeycomb memory footprint.
\ No newline at end of file
diff --git a/infra/footprint/footprint-api/pom.xml b/infra/footprint/footprint-api/pom.xml
new file mode 100644 (file)
index 0000000..cd9347a
--- /dev/null
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+  ~ Copyright (c) 2017 Cisco and/or its affiliates.
+  ~
+  ~ Licensed 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.
+  -->
+
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+    <parent>
+        <groupId>io.fd.honeycomb.common</groupId>
+        <artifactId>api-parent</artifactId>
+        <version>1.17.10-SNAPSHOT</version>
+        <relativePath>../../../common/api-parent</relativePath>
+    </parent>
+    <modelVersion>4.0.0</modelVersion>
+
+    <groupId>io.fd.honeycomb.footprint</groupId>
+    <artifactId>api</artifactId>
+    <version>1.17.10-SNAPSHOT</version>
+    <name>${project.artifactId}</name>
+    <packaging>jar</packaging>
+</project>
\ No newline at end of file
diff --git a/infra/footprint/footprint-api/src/main/yang/footprint.yang b/infra/footprint/footprint-api/src/main/yang/footprint.yang
new file mode 100644 (file)
index 0000000..680f15c
--- /dev/null
@@ -0,0 +1,28 @@
+module footprint {
+  yang-version 1;
+  namespace "urn:opendaylight:params:xml:ns:yang:footprint";
+  prefix "footprint";
+
+  revision "2017-08-30" {
+    description "HC model for requesting current memory consumption";
+  }
+
+  container memory-footprint-state {
+    config false;
+
+    leaf footprint {
+        type uint32;
+        description "Memory footprint in kilobytes. Footprint is parsed as output of ps command, where RSS field is
+         read.
+
+         RSS is the Resident Set Size and is used to show how much memory is allocated to that process and is in RAM.
+         It does not include memory that is swapped out. It does include memory from shared libraries
+         as long as the pages from those libraries are actually in memory. It does include all stack and heap memory.";
+    }
+
+    leaf pid {
+        type uint32;
+        description "Process id of honeycomb";
+    }
+  }
+}
diff --git a/infra/footprint/footprint-impl/asciidoc/Readme.adoc b/infra/footprint/footprint-impl/asciidoc/Readme.adoc
new file mode 100644 (file)
index 0000000..79306b5
--- /dev/null
@@ -0,0 +1,19 @@
+= impl
+
+== To read footprint
+
+[source,java]
+----
+HttpResponse<String> response = Unirest.get("http://localhost:8183/restconf/operational/footprint:memory-footprint-state")
+  .header("authorization", "Basic YWRtaW46YWRtaW4=")
+  .header("content-type", "application/json")
+  .asString();
+----
+
+[source,shell]
+----
+curl --request GET \
+  --url http://localhost:8183/restconf/operational/footprint:memory-footprint-state \
+  --header 'authorization: Basic YWRtaW46YWRtaW4=' \
+  --header 'content-type: application/json'
+----
\ No newline at end of file
diff --git a/infra/footprint/footprint-impl/pom.xml b/infra/footprint/footprint-impl/pom.xml
new file mode 100644 (file)
index 0000000..6649f7f
--- /dev/null
@@ -0,0 +1,69 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+  ~ Copyright (c) 2017 Cisco and/or its affiliates.
+  ~
+  ~ Licensed 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.
+  -->
+
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+    <parent>
+        <groupId>io.fd.honeycomb.common</groupId>
+        <artifactId>impl-parent</artifactId>
+        <version>1.17.10-SNAPSHOT</version>
+        <relativePath>../../../common/impl-parent</relativePath>
+    </parent>
+    <modelVersion>4.0.0</modelVersion>
+
+    <groupId>io.fd.honeycomb.footprint</groupId>
+    <artifactId>impl</artifactId>
+    <version>1.17.10-SNAPSHOT</version>
+    <name>${project.artifactId}</name>
+
+    <dependencies>
+        <dependency>
+            <groupId>io.fd.honeycomb.footprint</groupId>
+            <artifactId>api</artifactId>
+            <version>${project.version}</version>
+        </dependency>
+        <dependency>
+            <groupId>org.slf4j</groupId>
+            <artifactId>slf4j-api</artifactId>
+            <version>${slf4j.version}</version>
+        </dependency>
+        <dependency>
+            <groupId>io.fd.honeycomb</groupId>
+            <artifactId>translate-api</artifactId>
+            <version>${project.version}</version>
+        </dependency>
+        <dependency>
+            <groupId>io.fd.honeycomb</groupId>
+            <artifactId>translate-spi</artifactId>
+            <version>${project.version}</version>
+        </dependency>
+        <dependency>
+            <groupId>io.fd.honeycomb</groupId>
+            <artifactId>translate-impl</artifactId>
+            <version>${project.version}</version>
+        </dependency>
+        <dependency>
+            <groupId>com.google.inject</groupId>
+            <artifactId>guice</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>com.google.inject.extensions</groupId>
+            <artifactId>guice-multibindings</artifactId>
+        </dependency>
+    </dependencies>
+</project>
\ No newline at end of file
diff --git a/infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintCustomizer.java b/infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintCustomizer.java
new file mode 100644 (file)
index 0000000..6d1db67
--- /dev/null
@@ -0,0 +1,55 @@
+/*
+ * Copyright (c) 2017 Cisco and/or its affiliates.
+ *
+ * Licensed 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 io.fd.honeycomb.footprint;
+
+import io.fd.honeycomb.translate.read.ReadContext;
+import io.fd.honeycomb.translate.read.ReadFailedException;
+import io.fd.honeycomb.translate.spi.read.ReaderCustomizer;
+import javax.annotation.Nonnull;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.footprint.rev170830.MemoryFootprintState;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.footprint.rev170830.MemoryFootprintStateBuilder;
+import org.opendaylight.yangtools.concepts.Builder;
+import org.opendaylight.yangtools.yang.binding.DataObject;
+import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
+
+public class FootprintCustomizer implements ReaderCustomizer<MemoryFootprintState, MemoryFootprintStateBuilder> {
+
+    private final FootprintReader footprintReader;
+
+    public FootprintCustomizer(@Nonnull final FootprintReader footprintReader) {
+        this.footprintReader = footprintReader;
+    }
+
+    @Nonnull
+    @Override
+    public MemoryFootprintStateBuilder getBuilder(@Nonnull final InstanceIdentifier<MemoryFootprintState> id) {
+        return new MemoryFootprintStateBuilder();
+    }
+
+    @Override
+    public void readCurrentAttributes(@Nonnull final InstanceIdentifier<MemoryFootprintState> id,
+                                      @Nonnull final MemoryFootprintStateBuilder builder,
+                                      @Nonnull final ReadContext ctx) throws ReadFailedException {
+        builder.setFootprint((long) footprintReader.readCurrentFootprint()).setPid((long) footprintReader.getPid());
+    }
+
+    @Override
+    public void merge(@Nonnull final Builder<? extends DataObject> parentBuilder,
+                      @Nonnull final MemoryFootprintState readValue) {
+        //NOOP
+    }
+}
diff --git a/infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintModule.java b/infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintModule.java
new file mode 100644 (file)
index 0000000..6792d71
--- /dev/null
@@ -0,0 +1,31 @@
+/*
+ * Copyright (c) 2017 Cisco and/or its affiliates.
+ *
+ * Licensed 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 io.fd.honeycomb.footprint;
+
+import com.google.inject.AbstractModule;
+import com.google.inject.multibindings.Multibinder;
+import io.fd.honeycomb.translate.read.ReaderFactory;
+
+public class FootprintModule extends AbstractModule {
+    @Override
+    protected void configure() {
+        final Multibinder<ReaderFactory> setBinder =
+                Multibinder.newSetBinder(binder(), ReaderFactory.class);
+        setBinder.addBinding().to(FootprintReaderFactory.class);
+        bind(FootprintReader.class).to(FootprintReaderImpl.class).asEagerSingleton();
+    }
+}
diff --git a/infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintReader.java b/infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintReader.java
new file mode 100644 (file)
index 0000000..28e5f77
--- /dev/null
@@ -0,0 +1,33 @@
+/*
+ * Copyright (c) 2017 Cisco and/or its affiliates.
+ *
+ * Licensed 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 io.fd.honeycomb.footprint;
+
+/**
+ * Allows reading of footprint of its own JVM
+ */
+public interface FootprintReader {
+
+    /**
+     * @return Nr of kilobytes occupied by this JVM
+     */
+    int readCurrentFootprint();
+
+    /**
+     * @return Process id associated with this JVM
+     */
+    int getPid();
+}
diff --git a/infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintReaderFactory.java b/infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintReaderFactory.java
new file mode 100644 (file)
index 0000000..0ff54c8
--- /dev/null
@@ -0,0 +1,37 @@
+/*
+ * Copyright (c) 2017 Cisco and/or its affiliates.
+ *
+ * Licensed 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 io.fd.honeycomb.footprint;
+
+import com.google.inject.Inject;
+import io.fd.honeycomb.translate.impl.read.GenericReader;
+import io.fd.honeycomb.translate.read.ReaderFactory;
+import io.fd.honeycomb.translate.read.registry.ModifiableReaderRegistryBuilder;
+import javax.annotation.Nonnull;
+import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.footprint.rev170830.MemoryFootprintState;
+import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
+
+public class FootprintReaderFactory implements ReaderFactory {
+
+    @Inject
+    private FootprintReader footprintReader;
+
+    @Override
+    public void init(@Nonnull final ModifiableReaderRegistryBuilder registry) {
+        registry.add(new GenericReader(InstanceIdentifier.create(MemoryFootprintState.class),
+                new FootprintCustomizer(footprintReader)));
+    }
+}
diff --git a/infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintReaderImpl.java b/infra/footprint/footprint-impl/src/main/java/io/fd/honeycomb/footprint/FootprintReaderImpl.java
new file mode 100644 (file)
index 0000000..817c5d4
--- /dev/null
@@ -0,0 +1,74 @@
+/*
+ * Copyright (c) 2017 Cisco and/or its affiliates.
+ *
+ * Licensed 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 io.fd.honeycomb.footprint;
+
+import static java.lang.String.format;
+
+import com.google.common.base.Charsets;
+import com.google.common.io.CharStreams;
+import java.io.BufferedInputStream;
+import java.io.IOException;
+import java.io.InputStreamReader;
+import java.lang.management.ManagementFactory;
+import java.util.Arrays;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+class FootprintReaderImpl implements FootprintReader {
+
+    private static final Logger LOG = LoggerFactory.getLogger(FootprintReaderImpl.class);
+
+    private final int pid;
+
+    public FootprintReaderImpl() {
+        pid = initPID();
+        LOG.info("Footprint marker initialized for pid {}", pid);
+    }
+
+
+    private static int initPID() {
+        final String processName = ManagementFactory.getRuntimeMXBean().getName();
+        return Integer.parseInt(processName.substring(0, processName.indexOf("@")));
+    }
+
+    @Override
+    public int readCurrentFootprint() {
+        try {
+            final Process process = Runtime.getRuntime().exec(" ps -eo rss,pid");
+
+            final BufferedInputStream input = new BufferedInputStream(process.getInputStream());
+            final String processOut = CharStreams.toString(new InputStreamReader(input, Charsets.UTF_8));
+
+            final String pidLine = Arrays.stream(processOut.split(System.lineSeparator()))
+                    .skip(1)// skip header
+                    .map(String::trim)
+                    .filter(line -> Integer.parseInt(line.split("\\s+")[1]) == pid)
+                    .findFirst()
+                    .orElseThrow(
+                            () -> new IllegalStateException(format("Unable to find memory stats for pid %s", pid)));
+
+            return Integer.parseInt(pidLine.split(" ")[0]);
+        } catch (IOException e) {
+            throw new IllegalStateException(e);
+        }
+    }
+
+    @Override
+    public int getPid() {
+        return pid;
+    }
+}
diff --git a/infra/footprint/pom.xml b/infra/footprint/pom.xml
new file mode 100644 (file)
index 0000000..adb7274
--- /dev/null
@@ -0,0 +1,35 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+  ~ Copyright (c) 2017 Cisco and/or its affiliates.
+  ~
+  ~ Licensed 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.
+  -->
+
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+    <parent>
+        <artifactId>infra-aggregator</artifactId>
+        <groupId>io.fd.honeycomb</groupId>
+        <version>1.17.10-SNAPSHOT</version>
+    </parent>
+    <modelVersion>4.0.0</modelVersion>
+
+    <groupId>io.fd.honeycomb.footprint</groupId>
+    <artifactId>footprint-aggregator</artifactId>
+    <packaging>pom</packaging>
+    <modules>
+        <module>footprint-api</module>
+        <module>footprint-impl</module>
+    </modules>
+</project>
\ No newline at end of file
index d8d1fc3..94e230a 100644 (file)
@@ -43,7 +43,8 @@
             io.fd.honeycomb.infra.distro.cfgattrs.CfgAttrsModule,
             // io.fd.honeycomb.infra.bgp.BgpModule,
             // io.fd.honeycomb.infra.bgp.BgpReadersModule,
-            // io.fd.honeycomb.infra.bgp.BgpWritersModule
+            // io.fd.honeycomb.infra.bgp.BgpWritersModule,
+            // io.fd.honeycomb.footprint.FootprintModule
         </distribution.modules>
     </properties>
 
             <artifactId>bgp</artifactId>
             <version>${project.version}</version>
         </dependency>
+        <dependency>
+            <groupId>io.fd.honeycomb.footprint</groupId>
+            <artifactId>impl</artifactId>
+            <version>${project.version}</version>
+        </dependency>
     </dependencies>
 </project>
index 040fc93..57fcb8f 100644 (file)
@@ -51,6 +51,7 @@
     <module>minimal-distribution-core</module>
     <module>northbound</module>
     <module>binding-init</module>
+    <module>footprint</module>
   </modules>
 
   <!-- DO NOT install or deploy the repo root pom as it's only needed to initiate a build -->