AboutServicesExperienceProjectsBlogContactResume Buy Me a Coffee Start a Project
Back to Blog
Building integration-smoke-test: A Python Tool for API Diagnostics
Technical
Jan 20, 2026·4 min read·By Rugved Chandekar

Building integration-smoke-test: A Python Tool for API Diagnostics

PythonOpen SourceAPI TestingDevTools

Every developer who works with APIs has been there: an integration fails, and the error message is useless. "Connection refused." "Request timed out." "Cannot resolve host." None of these tell you why.

Is it a DNS issue? A firewall block? A timeout configuration problem? A wrong endpoint? Finding out means manual investigation — ping, nslookup, curl with verbose flags, checking environment variables. It's tedious, repetitive, and it's a problem worth solving properly.

That's what I built integration-smoke-test to address.

The Problem

Integration failures happen at multiple layers:

  • DNS resolution — the hostname can't be resolved
  • Network connectivity — the host is reachable but a port is blocked
  • TLS/SSL — certificate issues preventing secure connections
  • Timeouts — the server is reachable but not responding in time
  • Endpoint failures — the connection succeeds but the API returns an error

A basic health check that just reports "failed" tells you nothing. You need layered diagnostics that identify which layer failed and why.

What integration-smoke-test Does

integration-smoke-test is a lightweight Python library that performs quick connectivity checks and provides structured diagnostic output when something goes wrong. Instead of just reporting failure, it identifies the probable cause and suggests next steps.

Example Usage

from integration_smoke_test import SmokeTest

# Basic connectivity check
test = SmokeTest("https://api.example.com/health")
result = test.run()

print(result.status)       # "pass" | "fail"
print(result.latency_ms)   # 142.3
print(result.diagnosis)    # Human-readable diagnosis
print(result.error_type)   # "dns_failure" | "timeout" | "ssl_error" | etc.
print(result.suggestion)   # Actionable next step

A failing result might look like:

{
  "status": "fail",
  "url": "https://api.internal.example.com/health",
  "latency_ms": null,
  "error_type": "dns_failure",
  "diagnosis": "DNS resolution failed for 'api.internal.example.com'. The hostname could not be resolved.",
  "suggestion": "Check that the hostname is correct and that your DNS server can resolve internal domains. If this is a VPN-dependent service, ensure your VPN is connected.",
  "checked_at": "2026-01-20T10:23:45Z"
}

Compare this to a raw Python requests exception: ConnectionError: HTTPSConnectionPool(host='api.internal.example.com', port=443): Max retries exceeded with url: /health (Caused by NewConnectionError(...: [Errno -2] Name or service not known)). Technically accurate; practically unhelpful.

Key Features

  • Layered diagnostics — checks DNS, TCP connectivity, TLS, and HTTP status in sequence, reporting which layer failed
  • Structured output — results are dataclasses/dicts, not just strings — easy to integrate into CI pipelines or monitoring
  • Latency measurement — reports round-trip time for successful connections
  • Error classification — categorizes failures into named types for programmatic handling
  • Actionable suggestions — plain-English guidance on what to check for each failure type
  • Batch testing — check multiple endpoints at once and get a summary report

Architecture

The library is structured as a pipeline of checks:

SmokeTest.run()
  │
  ├─► DNS Resolution Check
  │     socket.getaddrinfo() with timeout
  │     → dns_failure if this fails
  │
  ├─► TCP Connectivity Check  
  │     socket.connect() to host:port
  │     → tcp_failure if this fails
  │
  ├─► TLS Handshake (HTTPS only)
  │     ssl.wrap_socket() verification
  │     → ssl_error if this fails
  │
  └─► HTTP Request
        requests.get() with timeout
        → timeout if no response
        → http_error if non-2xx status
        → pass if 2xx response

Each stage only runs if the previous one passed. The first failure determines the diagnosis. This mirrors how a developer would manually debug a connectivity issue — check each layer in order.

Publishing to PyPI

Getting a package onto PyPI is straightforward with modern tooling:

# Install build tools
pip install build twine

# Build the distribution
python -m build

# Upload to PyPI
python -m twine upload dist/*

# Install from PyPI
pip install integration-smoke-test

The key files needed: pyproject.toml with package metadata, a clean src/ layout, and a README.md that serves as the PyPI description page.

What I Learned

  • API design matters as much as functionality — the ergonomics of how a library is used shapes its adoption more than feature completeness
  • Error messages are a user interface — clear, actionable error output is as important as correct behavior
  • Python packaging has improved dramaticallypyproject.toml and build/twine make publishing straightforward
  • Small, focused tools have real value — doing one thing well is more useful than doing many things adequately

The library is available on PyPI and GitHub. If you're debugging integration failures or want to add connectivity diagnostics to your CI pipeline, give it a try.

Using the library or have ideas to improve it? Contributions welcome on GitHub.

Get In Touch
RC
Rugved Chandekar AI Systems Engineer @ Idyllic Services — Python Tools & PyPI — IEEE Author