Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(sqlalchemy): Guard against engine.url being None #2708

Merged
merged 3 commits into from Feb 6, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
3 changes: 3 additions & 0 deletions sentry_sdk/integrations/sqlalchemy.py
Expand Up @@ -153,6 +153,9 @@ def _set_db_data(span, conn):
if db_system is not None:
span.set_data(SPANDATA.DB_SYSTEM, db_system)

if conn.engine.url is None:
return

db_name = conn.engine.url.database
if db_name is not None:
span.set_data(SPANDATA.DB_NAME, db_name)
Expand Down
56 changes: 56 additions & 0 deletions tests/integrations/sqlalchemy/test_sqlalchemy.py
Expand Up @@ -154,6 +154,62 @@ class Address(Base):
)


@pytest.mark.skipif(
sys.version_info < (3,), reason="This sqla usage seems to be broken on Py2"
)
def test_transactions_no_engine_url(sentry_init, capture_events):
sentry_init(
integrations=[SqlalchemyIntegration()],
_experiments={"record_sql_params": True},
traces_sample_rate=1.0,
)
events = capture_events()

Base = declarative_base() # noqa: N806

class Person(Base):
__tablename__ = "person"
id = Column(Integer, primary_key=True)
name = Column(String(250), nullable=False)

class Address(Base):
__tablename__ = "address"
id = Column(Integer, primary_key=True)
street_name = Column(String(250))
street_number = Column(String(250))
post_code = Column(String(250), nullable=False)
person_id = Column(Integer, ForeignKey("person.id"))
person = relationship(Person)

engine = create_engine("sqlite:///:memory:")
engine.url = None
Base.metadata.create_all(engine)

Session = sessionmaker(bind=engine) # noqa: N806
session = Session()

with start_transaction(name="test_transaction", sampled=True):
with session.begin_nested():
session.query(Person).first()

for _ in range(2):
with pytest.raises(IntegrityError):
with session.begin_nested():
session.add(Person(id=1, name="bob"))
session.add(Person(id=1, name="bob"))

with session.begin_nested():
session.query(Person).first()

(event,) = events

for span in event["spans"]:
assert span["data"][SPANDATA.DB_SYSTEM] == "sqlite"
assert SPANDATA.DB_NAME not in span["data"]
assert SPANDATA.SERVER_ADDRESS not in span["data"]
assert SPANDATA.SERVER_PORT not in span["data"]


def test_long_sql_query_preserved(sentry_init, capture_events):
sentry_init(
traces_sample_rate=1,
Expand Down