Find an API

Search public APIs with auth details & Postman guides

← All APIs

U.S. EPA Enforcement and Compliance History Online (ECHO) - Detailed Facility Report (DFR)

epa · Government

Government No Auth Free & Open open_data

Enforcement and Compliance History Online (ECHO) is a tool developed and maintained by EPA's Office of Enforcement and Compliance Assurance for public use. ECHO provides integrated compliance and enforcement information for over 1 million regulated facilities nationwide. DFR Rest Services provide multiple service endpoints, to retrieve detailed facility location, enforcement, compliance monitoring, and pollutant information for any single facility. See the Detailed Facility Report (DFR) Help P

Authentication

No authentication requiredFree to use with no key needed.

Sample Requests

GET Downloads the complete Air Compliance History Section of the DFR

For the provided system identifier, dowloads all displayed Air quaterly/monthly Facility Level Status, High Priority Violation (HPV) History, HPV Detailed Violations and Federal Reportable Violation information in a Comma Seperated Value (CSV) format.

https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.air_3_yr_download

Hover any highlighted part to learn what it does

curl -X GET "https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.air_3_yr_download"
import requests
response = requests.get(
    "https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.air_3_yr_download",
)
print(response.json())
const url = 'https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.air_3_yr_download';

const response = await fetch(url); 
const data = await response.json();
console.log(data);
package main

import (
	"fmt"
	"io"
	"net/http"
)

func main() {
	targetURL := "https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.air_3_yr_download"
	req, _ := http.NewRequest("GET", targetURL, nil)

	client := &http.Client{}
	resp, _ := client.Do(req)
	defer resp.Body.Close()
	body, _ := io.ReadAll(resp.Body)
	fmt.Println(string(body))
}
require "net/http"
require "json"

uri = URI("https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.air_3_yr_download")

http = Net::HTTP.new(uri.host, uri.port)
http.use_ssl = uri.scheme == "https"

req = Net::HTTP::Get.new(uri)

res = http.request(req)
puts JSON.parse(res.body)
<?php
$url = "https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.air_3_yr_download";
$opts = ["http" => [
    "method" => "GET",
]];
$ctx = stream_context_create($opts);
$res = file_get_contents($url, false, $ctx);
print_r(json_decode($res, true));
GET Downloads NPDES Effluent Violation Information by month and quarter.

For the provided system identifier, dowloads all displayed NPDES quaterly/monthly effluent violation information in a Comma Seperated Value (CSV) format.

https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_effluent_download

Hover any highlighted part to learn what it does

curl -X GET "https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_effluent_download"
import requests
response = requests.get(
    "https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_effluent_download",
)
print(response.json())
const url = 'https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_effluent_download';

const response = await fetch(url); 
const data = await response.json();
console.log(data);
package main

import (
	"fmt"
	"io"
	"net/http"
)

func main() {
	targetURL := "https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_effluent_download"
	req, _ := http.NewRequest("GET", targetURL, nil)

	client := &http.Client{}
	resp, _ := client.Do(req)
	defer resp.Body.Close()
	body, _ := io.ReadAll(resp.Body)
	fmt.Println(string(body))
}
require "net/http"
require "json"

uri = URI("https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_effluent_download")

http = Net::HTTP.new(uri.host, uri.port)
http.use_ssl = uri.scheme == "https"

req = Net::HTTP::Get.new(uri)

res = http.request(req)
puts JSON.parse(res.body)
<?php
$url = "https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_effluent_download";
$opts = ["http" => [
    "method" => "GET",
]];
$ctx = stream_context_create($opts);
$res = file_get_contents($url, false, $ctx);
print_r(json_decode($res, true));
GET Downloads NPDES Compliance Schedule, Permit Schedule and Single Event Violation Information by month and quarter.

For the provided system identifier, dowloads all displayed NPDES quaterly/monthly Compliance Schedule, Permit Schedule, and Single Event Violation information in a Comma Seperated Value (CSV) format.

https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_sepscs_download

Hover any highlighted part to learn what it does

curl -X GET "https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_sepscs_download"
import requests
response = requests.get(
    "https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_sepscs_download",
)
print(response.json())
const url = 'https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_sepscs_download';

const response = await fetch(url); 
const data = await response.json();
console.log(data);
package main

import (
	"fmt"
	"io"
	"net/http"
)

func main() {
	targetURL := "https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_sepscs_download"
	req, _ := http.NewRequest("GET", targetURL, nil)

	client := &http.Client{}
	resp, _ := client.Do(req)
	defer resp.Body.Close()
	body, _ := io.ReadAll(resp.Body)
	fmt.Println(string(body))
}
require "net/http"
require "json"

uri = URI("https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_sepscs_download")

http = Net::HTTP.new(uri.host, uri.port)
http.use_ssl = uri.scheme == "https"

req = Net::HTTP::Get.new(uri)

res = http.request(req)
puts JSON.parse(res.body)
<?php
$url = "https://api.apis.guru/v2/specs/epa.gov/dfr/0.0.0/dfr_rest_services.cwa_3_yr_sepscs_download";
$opts = ["http" => [
    "method" => "GET",
]];
$ctx = stream_context_create($opts);
$res = file_get_contents($url, false, $ctx);
print_r(json_decode($res, true));

Postman Setup Guide

Get Postman ↗
  1. See official documentation for authentication and setup.

What can you build with U.S. EPA Enforcement and Compliance History Online (ECHO) - Detailed Facility Report (DFR)?

U.S. EPA Enforcement and Compliance History Online (ECHO) - Detailed Facility Report (DFR) is a Government API. Developers commonly use government APIs for:

  • surfacing public datasets in citizen-facing apps
  • building transparency and civic engagement tools
  • accessing legislation, court records, and official data
  • powering research and journalism tools
  • creating compliance and regulatory monitoring dashboards

No authentication required. This API is open — no signup or key needed. Ideal for quick prototypes and public-facing features. U.S. EPA Enforcement and Compliance History Online (ECHO) - Detailed Facility Report (DFR) is free to use, making it a low-risk choice to experiment with.

New to APIs? Read our beginner's guide · Learn about API keys · What is REST?

Open documentation ↗