diff --git a/instrumentation-security/jdbc-mariadb-3.0.0/build.gradle b/instrumentation-security/jdbc-mariadb-3.0.0/build.gradle new file mode 100644 index 000000000..722f3893d --- /dev/null +++ b/instrumentation-security/jdbc-mariadb-3.0.0/build.gradle @@ -0,0 +1,22 @@ +dependencies { + implementation(project(":newrelic-security-api")) + implementation("com.newrelic.agent.java:newrelic-api:${nrAPIVersion}") + implementation("com.newrelic.agent.java:newrelic-weaver-api:${nrAPIVersion}") + implementation("org.mariadb.jdbc:mariadb-java-client:3.0.3") + + testImplementation ("ch.vorburger.mariaDB4j:mariaDB4j:2.2.1") +} + +jar { + manifest { attributes 'Implementation-Title': 'com.newrelic.instrumentation.security.jdbc-mariadb-3.0.0' } +} + +verifyInstrumentation { + passesOnly 'org.mariadb.jdbc:mariadb-java-client:(3.0.2-rc,)' + exclude 'org.mariadb.jdbc:mariadb-java-client:[3.0.0-alpha,3.0.2-rc]' +} + +site { + title 'MariaDB Java Client' + type 'Datastore' +} \ No newline at end of file diff --git a/instrumentation-security/jdbc-mariadb-3.0.0/src/main/java/org/mariadb/jdbc/Driver.java b/instrumentation-security/jdbc-mariadb-3.0.0/src/main/java/org/mariadb/jdbc/Driver.java new file mode 100644 index 000000000..5bfbb3fcf --- /dev/null +++ b/instrumentation-security/jdbc-mariadb-3.0.0/src/main/java/org/mariadb/jdbc/Driver.java @@ -0,0 +1,21 @@ +package org.mariadb.jdbc; + +import com.newrelic.api.agent.security.NewRelicSecurity; +import com.newrelic.api.agent.security.schema.JDBCVendor; +import com.newrelic.api.agent.weaver.Weave; +import com.newrelic.api.agent.weaver.Weaver; +import org.mariadb.jdbc.Connection; + +import java.util.Properties; + +@Weave +public abstract class Driver { + + public Connection connect(String url, Properties props) { + if(NewRelicSecurity.getAgent().getSecurityMetaData() != null && !NewRelicSecurity.getAgent().getSecurityMetaData().getRequest().isEmpty()) { + NewRelicSecurity.getAgent().getSecurityMetaData().addCustomAttribute(JDBCVendor.META_CONST_JDBC_VENDOR, JDBCVendor.MARIA_DB); + } + return Weaver.callOriginal(); + } + +} diff --git a/instrumentation-security/jdbc-mariadb-3.0.0/src/main/java/org/mariadb/jdbc/MariaDbDataSource_Instrumentation.java b/instrumentation-security/jdbc-mariadb-3.0.0/src/main/java/org/mariadb/jdbc/MariaDbDataSource_Instrumentation.java new file mode 100644 index 000000000..e54e60409 --- /dev/null +++ b/instrumentation-security/jdbc-mariadb-3.0.0/src/main/java/org/mariadb/jdbc/MariaDbDataSource_Instrumentation.java @@ -0,0 +1,29 @@ +package org.mariadb.jdbc; + +import com.newrelic.api.agent.security.NewRelicSecurity; +import com.newrelic.api.agent.security.schema.JDBCVendor; +import com.newrelic.api.agent.weaver.MatchType; +import com.newrelic.api.agent.weaver.Weave; +import com.newrelic.api.agent.weaver.Weaver; + +import java.sql.SQLException; +import java.sql.Connection; + +@Weave(type = MatchType.ExactClass, originalName = "org.mariadb.jdbc.MariaDbDataSource") +public abstract class MariaDbDataSource_Instrumentation { + + public Connection getConnection() throws SQLException { + if(NewRelicSecurity.getAgent().getSecurityMetaData() != null && !NewRelicSecurity.getAgent().getSecurityMetaData().getRequest().isEmpty()) { + NewRelicSecurity.getAgent().getSecurityMetaData().addCustomAttribute(JDBCVendor.META_CONST_JDBC_VENDOR, JDBCVendor.MARIA_DB); + } + return Weaver.callOriginal(); + } + + public Connection getConnection(String user, String password) throws SQLException { + if(NewRelicSecurity.getAgent().getSecurityMetaData() != null && !NewRelicSecurity.getAgent().getSecurityMetaData().getRequest().isEmpty()) { + NewRelicSecurity.getAgent().getSecurityMetaData().addCustomAttribute(JDBCVendor.META_CONST_JDBC_VENDOR, JDBCVendor.MARIA_DB); + } + return Weaver.callOriginal(); + } + +} \ No newline at end of file diff --git a/instrumentation-security/jdbc-mariadb-3.0.0/src/test/java/com/nr/agent/security/instrumentation/jdbc/mariadb300/DataSourceTest.java b/instrumentation-security/jdbc-mariadb-3.0.0/src/test/java/com/nr/agent/security/instrumentation/jdbc/mariadb300/DataSourceTest.java new file mode 100644 index 000000000..17cd9f2bd --- /dev/null +++ b/instrumentation-security/jdbc-mariadb-3.0.0/src/test/java/com/nr/agent/security/instrumentation/jdbc/mariadb300/DataSourceTest.java @@ -0,0 +1,119 @@ +package com.nr.agent.security.instrumentation.jdbc.mariadb300; + +import ch.vorburger.mariadb4j.DB; +import ch.vorburger.mariadb4j.DBConfigurationBuilder; +import com.newrelic.agent.security.introspec.InstrumentationTestConfig; +import com.newrelic.agent.security.introspec.SecurityInstrumentationTestRunner; +import com.newrelic.agent.security.introspec.SecurityIntrospector; +import com.newrelic.api.agent.Trace; +import com.newrelic.api.agent.security.schema.JDBCVendor; +import com.newrelic.api.agent.security.schema.StringUtils; +import org.junit.AfterClass; +import org.junit.Assert; +import org.junit.BeforeClass; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.mariadb.jdbc.MariaDbDataSource; + +import java.sql.Connection; +import java.sql.SQLException; + +@RunWith(SecurityInstrumentationTestRunner.class) +@InstrumentationTestConfig(includePrefixes = {"org.mariadb.jdbc"}) +public class DataSourceTest { + private static DB mariaDb; + private static String connectionString; + private static final String DB_USER = ""; + private static final String DB_PASSWORD = ""; + + @BeforeClass + public static void setUpDb() throws Exception { + DBConfigurationBuilder builder = DBConfigurationBuilder.newBuilder() + .setPort(0); // This will automatically find a free port + + String dbName = "MariaDB" + System.currentTimeMillis(); + mariaDb = DB.newEmbeddedDB(builder.build()); + connectionString = StringUtils.replace(builder.getURL(dbName), "mysql", "mariadb"); + mariaDb.start(); + + mariaDb.createDB(dbName); + mariaDb.source("maria-db-test.sql", null, null, dbName); + } + @AfterClass + public static void tearDownDb() throws Exception { + mariaDb.stop(); + } + + @Test + public void testConnection() throws SQLException { + getConnection( new MariaDbDataSource()); + + SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector(); + String vendor = introspector.getJDBCVendor(); + Assert.assertEquals("Incorrect DB vendor", JDBCVendor.MARIA_DB, vendor); + } + + @Test + public void testConnection1() throws SQLException { + getConnection1(new MariaDbDataSource()); + + SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector(); + String vendor = introspector.getJDBCVendor(); + Assert.assertEquals("Incorrect DB vendor", JDBCVendor.MARIA_DB, vendor); + } + + @Test + public void testConnection2() throws SQLException { + getConnection( new MariaDbDataSource(connectionString)); + + SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector(); + String vendor = introspector.getJDBCVendor(); + Assert.assertEquals("Incorrect DB vendor", JDBCVendor.MARIA_DB, vendor); + } + + @Test + public void testConnection3() throws SQLException { + getConnection1(new MariaDbDataSource(connectionString)); + + SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector(); + String vendor = introspector.getJDBCVendor(); + Assert.assertEquals("Incorrect DB vendor", JDBCVendor.MARIA_DB, vendor); + } + + @Trace(dispatcher = true) + private void getConnection(MariaDbDataSource dataSource) throws SQLException { + Connection dbConnection = null; + + dataSource.setUrl(connectionString); + dataSource.setUser(DB_USER); + dataSource.setPassword(DB_PASSWORD); + try { + Class.forName("org.mariadb.jdbc.Driver"); + dbConnection = dataSource.getConnection(); + } catch (Exception e) { + e.printStackTrace(); + } + finally { + if (dbConnection!=null) { + dbConnection.close(); + } + } + } + + @Trace(dispatcher = true) + private void getConnection1(MariaDbDataSource dataSource) throws SQLException { + Connection dbConnection = null; + dataSource.setUrl(connectionString); + try { + Class.forName("org.mariadb.jdbc.Driver"); + dbConnection = dataSource.getConnection(DB_USER, DB_PASSWORD); + } catch (Exception e) { + e.printStackTrace(); + } + finally { + if (dbConnection!=null) { + dbConnection.close(); + } + } + } +} diff --git a/instrumentation-security/jdbc-mariadb-3.0.0/src/test/java/com/nr/agent/security/instrumentation/jdbc/mariadb300/MariaDb300Test.java b/instrumentation-security/jdbc-mariadb-3.0.0/src/test/java/com/nr/agent/security/instrumentation/jdbc/mariadb300/MariaDb300Test.java new file mode 100644 index 000000000..0c185fd41 --- /dev/null +++ b/instrumentation-security/jdbc-mariadb-3.0.0/src/test/java/com/nr/agent/security/instrumentation/jdbc/mariadb300/MariaDb300Test.java @@ -0,0 +1,70 @@ +/* + * + * * Copyright 2020 New Relic Corporation. All rights reserved. + * * SPDX-License-Identifier: Apache-2.0 + * + */ + +package com.nr.agent.security.instrumentation.jdbc.mariadb300; + +import ch.vorburger.mariadb4j.DB; +import ch.vorburger.mariadb4j.DBConfigurationBuilder; +import com.newrelic.agent.security.introspec.InstrumentationTestConfig; +import com.newrelic.agent.security.introspec.SecurityInstrumentationTestRunner; +import com.newrelic.agent.security.introspec.SecurityIntrospector; +import com.newrelic.api.agent.security.schema.JDBCVendor; +import com.newrelic.api.agent.security.schema.StringUtils; +import org.junit.AfterClass; +import org.junit.Assert; +import org.junit.BeforeClass; +import org.junit.Test; +import org.junit.runner.RunWith; + +import java.sql.Connection; +import java.sql.DriverManager; +import java.sql.SQLException; +import java.util.ArrayList; +import java.util.List; + +@RunWith(SecurityInstrumentationTestRunner.class) +@InstrumentationTestConfig(includePrefixes = {"org.mariadb.jdbc"}) +public class MariaDb300Test { + + private static DB mariaDb; + + private static String connectionString; + private static String dbName; + + private static Connection connection; + + private static List QUERIES = new ArrayList<>(); + + @BeforeClass + public static void setUpDb() throws Exception { + QUERIES.add("select * from testQuery"); + DBConfigurationBuilder builder = DBConfigurationBuilder.newBuilder() + .setPort(0); // This will automatically find a free port + + dbName = "MariaDB" + System.currentTimeMillis(); + mariaDb = DB.newEmbeddedDB(builder.build()); + connectionString = StringUtils.replace(builder.getURL(dbName), "mysql", "mariadb"); + mariaDb.start(); + + mariaDb.createDB(dbName); + mariaDb.source("maria-db-test.sql", null, null, dbName); + } + @AfterClass + public static void tearDownDb() throws Exception { + mariaDb.stop(); + } + + @Test + public void testConnect() throws SQLException, ClassNotFoundException { + Class.forName("org.mariadb.jdbc.Driver"); + connection = DriverManager.getConnection(connectionString, "root", ""); + + SecurityIntrospector introspector = SecurityInstrumentationTestRunner.getIntrospector(); + String vendor = introspector.getJDBCVendor(); + Assert.assertEquals("Incorrect DB vendor", vendor, JDBCVendor.MARIA_DB); + } +} diff --git a/instrumentation-security/jdbc-mariadb-3.0.0/src/test/resources/maria-db-test.sql b/instrumentation-security/jdbc-mariadb-3.0.0/src/test/resources/maria-db-test.sql new file mode 100644 index 000000000..ad8c763dd --- /dev/null +++ b/instrumentation-security/jdbc-mariadb-3.0.0/src/test/resources/maria-db-test.sql @@ -0,0 +1,6 @@ +CREATE TABLE testQuery (id int not null primary key, value varchar(20)); +INSERT INTO testQuery (id, value) VALUES (1, 'john'); +INSERT INTO testQuery (id, value) VALUES (2, 'monu'); +INSERT INTO testQuery (id, value) VALUES (3, 'sweet'); + +CREATE TABLE testCrud (id int not null primary key, value varchar(20)); \ No newline at end of file diff --git a/settings.gradle b/settings.gradle index afec08f66..1cdbcb261 100644 --- a/settings.gradle +++ b/settings.gradle @@ -66,6 +66,7 @@ include 'instrumentation:jdbc-hsqldb-1.7.2.2' include 'instrumentation:jdbc-hsqldb-2.2.9' include 'instrumentation:jdbc-mariadb-1.1.7' include 'instrumentation:jdbc-mariadb-1.3.0' +include 'instrumentation:jdbc-mariadb-3.0.0' include 'instrumentation:jdbc-jtds-generic' include 'instrumentation:jdbc-mysql-3.0.8' include 'instrumentation:jdbc-mysql-6.0.2'