Skip to content

Commit

Permalink
Merge branch 'main' into fix-psycopg2-instrument-connection
Browse files Browse the repository at this point in the history
  • Loading branch information
tammy-baylis-swi authored Dec 20, 2024
2 parents 0f7baec + 1092344 commit a2fa981
Show file tree
Hide file tree
Showing 8 changed files with 220 additions and 21 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -25,22 +25,39 @@
import aiopg
from opentelemetry.instrumentation.aiopg import AiopgInstrumentor
# Call instrument() to wrap all database connections
AiopgInstrumentor().instrument()
cnx = await aiopg.connect(database='Database')
cursor = await cnx.cursor()
await cursor.execute("CREATE TABLE IF NOT EXISTS test (testField INTEGER)")
await cursor.execute("INSERT INTO test (testField) VALUES (123)")
cursor.close()
cnx.close()
pool = await aiopg.create_pool(database='Database')
cnx = await pool.acquire()
cursor = await cnx.cursor()
await cursor.execute("CREATE TABLE IF NOT EXISTS test (testField INTEGER)")
await cursor.execute("INSERT INTO test (testField) VALUES (123)")
cursor.close()
cnx.close()
.. code-block:: python
import aiopg
from opentelemetry.instrumentation.aiopg import AiopgInstrumentor
# Alternatively, use instrument_connection for an individual connection
cnx = await aiopg.connect(database='Database')
instrumented_cnx = AiopgInstrumentor().instrument_connection(cnx)
cursor = await instrumented_cnx.cursor()
await cursor.execute("CREATE TABLE IF NOT EXISTS test (testField INTEGER)")
await cursor.execute("INSERT INTO test (testField) VALUES (123)")
cursor.close()
instrumented_cnx.close()
API
---
"""
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,14 +26,30 @@
import mysql.connector
from opentelemetry.instrumentation.mysql import MySQLInstrumentor
# Call instrument() to wrap all database connections
MySQLInstrumentor().instrument()
cnx = mysql.connector.connect(database="MySQL_Database")
cursor = cnx.cursor()
cursor.execute("CREATE TABLE IF NOT EXISTS test (testField INTEGER)")
cursor.execute("INSERT INTO test (testField) VALUES (123)")
cursor.close()
cnx.close()
.. code:: python
import mysql.connector
from opentelemetry.instrumentation.mysql import MySQLInstrumentor
# Alternatively, use instrument_connection for an individual connection
cnx = mysql.connector.connect(database="MySQL_Database")
instrumented_cnx = MySQLInstrumentor().instrument_connection(cnx)
cursor = instrumented_cnx.cursor()
cursor.execute("CREATE TABLE IF NOT EXISTS test (testField INTEGER)")
cursor.execute("INSERT INTO test (testField) VALUES (123)")
cursor.close()
instrumented_cnx.close()
API
---
"""
Expand Down Expand Up @@ -86,12 +102,16 @@ def instrument_connection(self, connection, tracer_provider=None):
"""Enable instrumentation in a MySQL connection.
Args:
connection: The connection to instrument.
tracer_provider: The optional tracer provider to use. If omitted
the current globally configured one is used.
connection:
The existing MySQL connection instance to instrument. This connection is typically
obtained through `mysql.connector.connect()` and is instrumented to collect telemetry
data about database interactions.
tracer_provider:
An optional `TracerProvider` instance to use for tracing. If not provided, the globally
configured tracer provider will be automatically used.
Returns:
An instrumented connection.
An instrumented MySQL connection with OpenTelemetry tracing enabled.
"""
return dbapi.instrument_connection(
__name__,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -46,16 +46,40 @@
import MySQLdb
from opentelemetry.instrumentation.mysqlclient import MySQLClientInstrumentor
# Call instrument() to wrap all database connections
MySQLClientInstrumentor().instrument(enable_commenter=True, commenter_options={})
cnx = MySQLdb.connect(database="MySQL_Database")
cursor = cnx.cursor()
cursor.execute("CREATE TABLE IF NOT EXISTS test (testField INTEGER)")
cursor.execute("INSERT INTO test (testField) VALUES (123)"
cnx.commit()
cursor.close()
cnx.close()
.. code:: python
import MySQLdb
from opentelemetry.instrumentation.mysqlclient import MySQLClientInstrumentor
# Alternatively, use instrument_connection for an individual connection
cnx = MySQLdb.connect(database="MySQL_Database")
instrumented_cnx = MySQLClientInstrumentor().instrument_connection(
cnx,
enable_commenter=True,
commenter_options={
"db_driver": True,
"mysql_client_version": True,
"driver_paramstyle": False
}
)
cursor = instrumented_cnx.cursor()
cursor.execute("CREATE TABLE IF NOT EXISTS test (testField INTEGER)")
cursor.execute("INSERT INTO test (testField) VALUES (123)"
instrumented_cnx.commit()
cursor.close()
instrumented_cnx.close()
For example,
::
Expand Down Expand Up @@ -162,12 +186,28 @@ def instrument_connection(
"""Enable instrumentation in a mysqlclient connection.
Args:
connection: The connection to instrument.
tracer_provider: The optional tracer provider to use. If omitted
the current globally configured one is used.
connection:
The MySQL connection instance to instrument. This connection is typically
created using `MySQLdb.connect()` and needs to be wrapped to collect telemetry.
tracer_provider:
A custom `TracerProvider` instance to be used for tracing. If not specified,
the globally configured tracer provider will be used.
enable_commenter:
A flag to enable the OpenTelemetry SQLCommenter feature. If set to `True`,
SQL queries will be enriched with contextual information (e.g., database client details).
Default is `None`.
commenter_options:
A dictionary of configuration options for SQLCommenter. All options are enabled (True) by default.
This allows you to customize metadata appended to queries. Possible options include:
- `db_driver`: Adds the database driver name and version.
- `dbapi_threadsafety`: Adds threadsafety information.
- `dbapi_level`: Adds the DB-API version.
- `mysql_client_version`: Adds the MySQL client version.
- `driver_paramstyle`: Adds the parameter style.
- `opentelemetry_values`: Includes traceparent values.
Returns:
An instrumented connection.
An instrumented MySQL connection with OpenTelemetry support enabled.
"""

return dbapi.instrument_connection(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -88,15 +88,31 @@
import psycopg
from opentelemetry.instrumentation.psycopg import PsycopgInstrumentor
# Call instrument() to wrap all database connections
PsycopgInstrumentor().instrument()
cnx = psycopg.connect(database='Database')
cursor = cnx.cursor()
cursor.execute("CREATE TABLE IF NOT EXISTS test (testField INTEGER)")
cursor.execute("INSERT INTO test (testField) VALUES (123)")
cursor.close()
cnx.close()
.. code-block:: python
import psycopg
from opentelemetry.instrumentation.psycopg import PsycopgInstrumentor
# Alternatively, use instrument_connection for an individual connection
cnx = psycopg.connect(database='Database')
instrumented_cnx = PsycopgInstrumentor().instrument_connection(cnx)
cursor = instrumented_cnx.cursor()
cursor.execute("CREATE TABLE IF NOT EXISTS test (testField INTEGER)")
cursor.execute("INSERT INTO test (testField) VALUES (123)")
cursor.close()
instrumented_cnx.close()
API
---
"""
Expand Down Expand Up @@ -196,6 +212,18 @@ def _uninstrument(self, **kwargs):
# TODO(owais): check if core dbapi can do this for all dbapi implementations e.g, pymysql and mysql
@staticmethod
def instrument_connection(connection, tracer_provider=None):
"""Enable instrumentation in a psycopg connection.
Args:
connection: psycopg.Connection
The psycopg connection object to be instrumented.
tracer_provider: opentelemetry.trace.TracerProvider, optional
The TracerProvider to use for instrumentation. If not provided,
the global TracerProvider will be used.
Returns:
An instrumented psycopg connection object.
"""
if not hasattr(connection, "_is_instrumented_by_opentelemetry"):
connection._is_instrumented_by_opentelemetry = False

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -88,15 +88,31 @@
import psycopg2
from opentelemetry.instrumentation.psycopg2 import Psycopg2Instrumentor
# Call instrument() to wrap all database connections
Psycopg2Instrumentor().instrument()
cnx = psycopg2.connect(database='Database')
cursor = cnx.cursor()
cursor.execute("CREATE TABLE IF NOT EXISTS test (testField INTEGER)")
cursor.execute("INSERT INTO test (testField) VALUES (123)")
cursor.close()
cnx.close()
.. code-block:: python
import psycopg2
from opentelemetry.instrumentation.psycopg2 import Psycopg2Instrumentor
# Alternatively, use instrument_connection for an individual connection
cnx = psycopg2.connect(database='Database')
instrumented_cnx = Psycopg2Instrumentor().instrument_connection(cnx)
cursor = instrumented_cnx.cursor()
cursor.execute("CREATE TABLE IF NOT EXISTS test (testField INTEGER)")
cursor.execute("INSERT INTO test (testField) VALUES (123)")
cursor.close()
instrumented_cnx.close()
API
---
"""
Expand Down Expand Up @@ -165,6 +181,18 @@ def instrument_connection(
connection,
tracer_provider: typing.Optional[trace_api.TracerProvider] = None,
):
"""Enable instrumentation in a psycopg2 connection.
Args:
connection: psycopg2.extensions.connection
The psycopg2 connection object to be instrumented.
tracer_provider: opentelemetry.trace.TracerProvider, optional
The TracerProvider to use for instrumentation. If not specified,
the global TracerProvider will be used.
Returns:
An instrumented psycopg2 connection object.
"""
if self._is_instrumented_by_opentelemetry:
# _instrument (via BaseInstrumentor) or instrument_connection (this)
# was already called
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
import pymysql
from opentelemetry.instrumentation.pymysql import PyMySQLInstrumentor
# Call instrument() to wrap all database connections
PyMySQLInstrumentor().instrument()
cnx = pymysql.connect(database="MySQL_Database")
Expand All @@ -35,6 +36,28 @@
cursor.close()
cnx.close()
.. code:: python
import pymysql
from opentelemetry.instrumentation.pymysql import PyMySQLInstrumentor
# Alternatively, use instrument_connection for an individual connection
cnx = pymysql.connect(database="MySQL_Database")
instrumented_cnx = PyMySQLInstrumentor().instrument_connection(
cnx,
enable_commenter=True,
commenter_options={
"db_driver": True,
"mysql_client_version": True
}
)
cursor = instrumented_cnx.cursor()
cursor.execute("INSERT INTO test (testField) VALUES (123)"
instrumented_cnx.commit()
cursor.close()
instrumented_cnx.close()
SQLCOMMENTER
*****************************************
You can optionally configure PyMySQL instrumentation to enable sqlcommenter which enriches
Expand Down Expand Up @@ -165,10 +188,20 @@ def instrument_connection(
"""Enable instrumentation in a PyMySQL connection.
Args:
connection: The connection to instrument.
tracer_provider: The optional tracer provider to use. If omitted
the current globally configured one is used.
connection:
The existing PyMySQL connection instance that needs to be instrumented.
This connection was typically created using `pymysql.connect()` and is wrapped with OpenTelemetry tracing.
tracer_provider:
An optional `TracerProvider` instance that specifies which tracer provider should be used.
If not provided, the globally configured OpenTelemetry tracer provider is automatically applied.
enable_commenter:
A flag to enable the SQL Commenter feature. If `True`, query logs will be enriched with additional
contextual metadata (e.g., database version, traceparent IDs, driver information).
commenter_options:
A dictionary containing configuration options for the SQL Commenter feature.
You can specify various options, such as enabling driver information, database version logging,
traceparent propagation, and other customizable metadata enhancements.
See *SQLCommenter Configurations* above for more information.
Returns:
An instrumented connection.
"""
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,16 +27,31 @@
import sqlite3
from opentelemetry.instrumentation.sqlite3 import SQLite3Instrumentor
# Call instrument() to wrap all database connections
SQLite3Instrumentor().instrument()
cnx = sqlite3.connect(':memory:')
cursor = cnx.cursor()
cursor.execute("CREATE TABLE test (testField INTEGER)")
cursor.execute("CREATE TABLE IF NOT EXISTS test (testField INTEGER)")
cursor.execute("INSERT INTO test (testField) VALUES (123)")
cursor.close()
cnx.close()
.. code:: python
import sqlite3
from opentelemetry.instrumentation.sqlite3 import SQLite3Instrumentor
# Alternatively, use instrument_connection for an individual connection
conn = sqlite3.connect(":memory:")
instrumented_connection = SQLite3Instrumentor().instrument_connection(conn)
cursor = instrumented_connection.cursor()
cursor.execute("CREATE TABLE IF NOT EXISTS test (testField INTEGER)")
cursor.execute("INSERT INTO test (testField) VALUES (123)")
cursor.execute("SELECT * FROM test")
cursor.close()
instrumented_connection.close()
API
---
"""
Expand Down Expand Up @@ -104,9 +119,10 @@ def instrument_connection(
the current globally configured one is used.
Returns:
An instrumented connection.
"""
An instrumented SQLite connection that supports
telemetry for tracing database operations.
"""
return dbapi.instrument_connection(
__name__,
connection,
Expand Down
Loading

0 comments on commit a2fa981

Please sign in to comment.