char.gy Open Charge Point Data API
char.gy's statutory open data feed, published to satisfy Part 4 regulation 10 of the UK Public Charge Point Regulations 2023, which requires reference data and availability data to be made available to the public free of charge, in a machine readable format, and without any requirement to agree to terms and conditions. It is shaped as an Open Charge Point Interface (OCPI) surface with exactly two modules exposed, both read-only GET and both completely unauthenticated. GET /open-ocpi/locations returned HTTP 200 and application/json to an anonymous request on 2026-07-27 with the OCPI envelope {data, status_code: 1000, status_message: "Success", timestamp}, an x-total-count of 5409 locations, a default x-limit of 50, and an RFC 5988 Link header advertising rel="next" — pagination is limit/offset via query string and was confirmed working at limit=2 and across offsets 0 to 550. Each location carries country_code GB, party_id CGY, a UUID id, parking_type (ON_STREET dominates, PARKING_LOT observed), publish, name, address, city, postal_code, country GBR, coordinates, an evses array, an operator block, an owner block naming the local authority, time_zone Europe/London, opening_times and last_updated. Every EVSE carries a uid, an evse_id of the form GB*CGY*E*00022, a status, capabilities (REMOTE_START_STOP_CAPABLE, UNLOCK_CAPABLE), a physical_reference and connectors describing IEC_62196_T2 sockets at AC_1_PHASE 230V/22A with tariff_ids and a terms_and_conditions link. GET /open-ocpi/tariffs returned HTTP 200 with 3 tariff objects carrying currency, elements and price_components of type ENERGY, including a real time-of-day tariff with weekday off-peak, weekday peak and weekend restrictions. No /open-ocpi /versions endpoint is served (404), so no OCPI version is declared, and the sessions, cdrs, tokens, commands and credentials modules are all 404 under /open-ocpi — only the two modules the regulation compels are open.
Documentation
Specifications
Other Resources
openapi: 3.1.0
info:
title: char.gy Open Charge Point Data API
version: '2026-07-27'
summary: >-
char.gy's statutory open data feed — an unauthenticated, OCPI-shaped
Locations and Tariffs surface published to satisfy Part 4 regulation 10 of
the UK Public Charge Point Regulations 2023.
description: >-
char.gy publishes no OpenAPI of its own; its entire published documentation
for this API is a single Freshdesk help-centre article naming the host and
two paths. This description was GENERATED by API Evangelist from live,
anonymous HTTP probes of the two published endpoints on 2026-07-27 — every
path, query parameter, response header, status code and schema field below
was observed in a real response, and nothing here was inferred from the OCPI
specification alone.
Observed behaviour: both endpoints answer HTTP 200 with
`application/json` to a request carrying no credential, no cookie and no
referer. Responses use the OCPI envelope `{data, status_code,
status_message, timestamp}` with `status_code: 1000` on success. Pagination
is limit/offset via query string, surfaced with `x-total-count`, `x-limit`
and an RFC 5988 `Link` header carrying `rel="next"`. `date_from` and
`date_to` filters are implemented and were verified to change
`x-total-count` (5409 unfiltered, 2396 for `date_from=2026-07-27T00:00:00Z`,
6 for `date_to=2026-07-01T00:00:00Z`, 0 for `date_from=2027-01-01T00:00:00Z`).
Bad parameter values return HTTP 200 with an OCPI client error envelope
(`status_code: 2001`), not a 4xx. Only GET and HEAD are routed; OPTIONS and
POST return 404. There is no `/open-ocpi/versions` endpoint (404), so no
OCPI version is declared, and the sessions, cdrs, tokens, commands and
credentials modules are all 404 under `/open-ocpi` — only the two modules
the regulation compels are open.
Enumerations below are constrained to values actually observed across a
250-location sample spanning offsets 0, 1000, 2500, 4000 and 5350; where the
observed value diverges from the OCPI 2.2.1 standard (notably EVSE `status`
values `WORKING` and `FAULTED`, which are not in the OCPI EVSEStatus
enumeration and appear to encode the regulator's "working" vocabulary from
regulation 10(6)(a)) the observed value is recorded, not corrected.
contact:
name: char.gy Support
email: support@char.gy
url: https://help.char.gy/
termsOfService: https://char.gy/us/terms-of-use
x-apievangelist-method: generated
x-apievangelist-source: >-
Live anonymous probes of https://char.gy/open-ocpi/locations and
https://char.gy/open-ocpi/tariffs, 2026-07-27
x-regulatory-basis: https://www.legislation.gov.uk/uksi/2023/1168/regulation/10/made
externalDocs:
description: char.gy help-centre article — Public Charge Point Regulations 2023
url: https://help.char.gy/support/solutions/articles/77000576948-public-charge-point-regulations-2023
servers:
- url: https://char.gy/open-ocpi
description: Production open data host (no authentication)
tags:
- name: Locations
description: Reference and availability data for char.gy charge points.
- name: Tariffs
description: Published price components for char.gy charging sessions.
paths:
/locations:
get:
tags: [Locations]
operationId: listLocations
summary: List charge point locations
description: >-
Returns the paginated list of char.gy charge point locations with their
EVSEs and connectors. Observed anonymously with HTTP 200 and an
`x-total-count` of 5409 on 2026-07-27. Every EVSE carries an
`evse_id` of the form `GB*CGY*E*NNNNN`; every connector carries
`tariff_ids` that resolve against `/tariffs`.
security: []
parameters:
- $ref: '#/components/parameters/limit'
- $ref: '#/components/parameters/offset'
- $ref: '#/components/parameters/dateFrom'
- $ref: '#/components/parameters/dateTo'
responses:
'200':
description: >-
OCPI envelope. `status_code` is 1000 on success; malformed
parameters also return HTTP 200 but with a 2xxx client error
status_code and no `data` member.
headers:
x-total-count:
$ref: '#/components/headers/XTotalCount'
x-limit:
$ref: '#/components/headers/XLimit'
link:
$ref: '#/components/headers/Link'
x-request-id:
$ref: '#/components/headers/XRequestId'
etag:
$ref: '#/components/headers/ETag'
content:
application/json:
schema:
oneOf:
- $ref: '#/components/schemas/LocationListResponse'
- $ref: '#/components/schemas/ErrorResponse'
examples:
success:
summary: Two locations (observed 2026-07-27, limit=2)
externalValue: ../examples/chargy-locations-response.json
badLimit:
summary: Non-numeric limit (observed 2026-07-27)
value:
status_code: 2001
status_message: Limit is not a number
timestamp: '2026-07-27T21:10:38Z'
/tariffs:
get:
tags: [Tariffs]
operationId: listTariffs
summary: List charging tariffs
description: >-
Returns the published tariff objects referenced by connector
`tariff_ids` on `/locations`. Observed anonymously with HTTP 200 and an
`x-total-count` of 3 on 2026-07-27, including a GBP time-of-day tariff
with weekday off-peak, weekday peak and weekend restrictions.
security: []
parameters:
- $ref: '#/components/parameters/limit'
- $ref: '#/components/parameters/offset'
- $ref: '#/components/parameters/dateFrom'
- $ref: '#/components/parameters/dateTo'
responses:
'200':
description: OCPI envelope carrying tariff objects.
headers:
x-total-count:
$ref: '#/components/headers/XTotalCount'
x-limit:
$ref: '#/components/headers/XLimit'
link:
$ref: '#/components/headers/Link'
x-request-id:
$ref: '#/components/headers/XRequestId'
etag:
$ref: '#/components/headers/ETag'
content:
application/json:
schema:
oneOf:
- $ref: '#/components/schemas/TariffListResponse'
- $ref: '#/components/schemas/ErrorResponse'
examples:
success:
summary: All three tariffs (observed 2026-07-27)
externalValue: ../examples/chargy-tariffs-response.json
components:
parameters:
limit:
name: limit
in: query
required: false
description: >-
Page size. Default 50 (observed via the `x-limit` response header on an
unparameterised request). A non-numeric value returns status_code 2001.
schema:
type: integer
default: 50
offset:
name: offset
in: query
required: false
description: >-
Zero-based record offset. An offset beyond the collection returns an
empty `data` array with status_code 1000.
schema:
type: integer
default: 0
dateFrom:
name: date_from
in: query
required: false
description: >-
Return only objects with `last_updated` at or after this timestamp.
Verified functional — `date_from=2026-07-27T00:00:00Z` reduced
`x-total-count` from 5409 to 2396. An unparseable value returns
status_code 2001 "Date from is not a valid timestamp".
schema:
type: string
format: date-time
dateTo:
name: date_to
in: query
required: false
description: >-
Return only objects with `last_updated` before this timestamp. Verified
functional — `date_to=2026-07-01T00:00:00Z` returned an `x-total-count`
of 6.
schema:
type: string
format: date-time
headers:
XTotalCount:
description: Total number of objects matching the query, before pagination.
schema:
type: integer
example: 5409
XLimit:
description: Page size applied to this response.
schema:
type: integer
example: 50
Link:
description: RFC 5988 pagination link; carries rel="next" when more pages exist.
schema:
type: string
example: <https://char.gy/open-ocpi/locations?limit=2&offset=2>; rel="next"
XRequestId:
description: Per-request correlation id emitted on every response.
schema:
type: string
example: 48324f0b-2c70-4f8d-9d97-deb08a76770e
ETag:
description: Weak validator; responses are sent with cache-control private, must-revalidate.
schema:
type: string
schemas:
OcpiEnvelope:
type: object
description: The OCPI response envelope observed on every 200 response.
required: [status_code, status_message, timestamp]
properties:
status_code:
type: integer
description: OCPI status code. 1000 = Success; 2001 observed for invalid parameters.
example: 1000
status_message:
type: string
example: Success
timestamp:
type: string
format: date-time
example: '2026-07-27T21:10:22Z'
ErrorResponse:
allOf:
- $ref: '#/components/schemas/OcpiEnvelope'
description: >-
Client-error envelope returned with HTTP 200 and no `data` member.
Observed messages: "Limit is not a number",
"Date from is not a valid timestamp".
LocationListResponse:
allOf:
- $ref: '#/components/schemas/OcpiEnvelope'
- type: object
required: [data]
properties:
data:
type: array
items:
$ref: '#/components/schemas/Location'
TariffListResponse:
allOf:
- $ref: '#/components/schemas/OcpiEnvelope'
- type: object
required: [data]
properties:
data:
type: array
items:
$ref: '#/components/schemas/Tariff'
Location:
type: object
description: An OCPI-shaped charge point location. Fields as observed.
required:
- country_code
- party_id
- id
- parking_type
- publish
- name
- address
- city
- postal_code
- country
- coordinates
- evses
- operator
- time_zone
- opening_times
- last_updated
properties:
country_code:
type: string
example: GB
party_id:
type: string
description: OCPI party identifier for char.gy.
example: CGY
id:
type: string
format: uuid
example: 98632dfb-6751-45ec-b3a0-9066b749fdfa
parking_type:
type: string
description: Only ON_STREET was observed across the 250-location sample.
enum: [ON_STREET]
example: ON_STREET
publish:
type: boolean
name:
type: string
example: Opposite 25 Grovelands Road
address:
type: string
example: Grovelands Road
city:
type: string
example: Haringey
postal_code:
type: string
example: N15 6BT
country:
type: string
description: ISO 3166-1 alpha-3.
example: GBR
coordinates:
$ref: '#/components/schemas/GeoLocation'
evses:
type: array
items:
$ref: '#/components/schemas/EVSE'
operator:
$ref: '#/components/schemas/BusinessDetails'
owner:
allOf:
- $ref: '#/components/schemas/BusinessDetails'
description: >-
Usually the local authority that owns the street furniture (Tower
Hamlets, Southwark, Merton, Haringey, Buckinghamshire County Council
observed); sometimes char.gy itself. Absent on roughly 40 percent of
sampled records.
time_zone:
type: string
example: Europe/London
opening_times:
$ref: '#/components/schemas/Hours'
last_updated:
type: string
format: date-time
GeoLocation:
type: object
description: Coordinates are strings, as observed.
required: [latitude, longitude]
properties:
latitude:
type: string
example: '51.5784972'
longitude:
type: string
example: '-0.0641408'
BusinessDetails:
type: object
required: [name]
properties:
name:
type: string
example: char.gy
website:
type: string
format: uri
example: https://char.gy
Hours:
type: object
properties:
twentyfourseven:
type: boolean
description: Only twentyfourseven true was observed.
EVSE:
type: object
required: [uid, evse_id, status, capabilities, connectors, last_updated]
properties:
uid:
type: string
format: uuid
evse_id:
type: string
description: eMI3-style EVSE identifier issued under the GB*CGY operator prefix.
example: GB*CGY*E*00022
status:
type: string
description: >-
Observed values only. Neither WORKING nor FAULTED appears in the
OCPI 2.2.1 EVSEStatus enumeration; they align instead with the
"working" vocabulary of regulation 10(6)(a) of the Public Charge
Point Regulations 2023. Recorded as observed, not corrected.
enum: [WORKING, FAULTED]
example: WORKING
capabilities:
type: array
items:
type: string
enum: [REMOTE_START_STOP_CAPABLE, UNLOCK_CAPABLE]
connectors:
type: array
items:
$ref: '#/components/schemas/Connector'
physical_reference:
type: string
example: '00022'
last_updated:
type: string
format: date-time
Connector:
type: object
required: [id, standard, format, power_type, max_voltage, max_amperage, last_updated]
properties:
id:
type: string
example: '1'
standard:
type: string
description: IEC 62196 Type 2 was the only standard observed.
enum: [IEC_62196_T2]
format:
type: string
enum: [SOCKET]
power_type:
type: string
enum: [AC_1_PHASE]
max_voltage:
type: integer
example: 230
max_amperage:
type: integer
example: 22
tariff_ids:
type: array
description: Resolves against the id of a Tariff on /tariffs.
items:
type: string
format: uuid
terms_and_conditions:
type: string
format: uri
example: https://char.gy/terms-of-use
last_updated:
type: string
format: date-time
Tariff:
type: object
required: [country_code, party_id, id, currency, elements, last_updated]
properties:
country_code:
type: string
example: GB
party_id:
type: string
example: CGY
id:
type: string
format: uuid
currency:
type: string
description: >-
GBP, EUR and USD were all observed on GB/CGY tariff records;
recorded as observed.
example: GBP
elements:
type: array
items:
$ref: '#/components/schemas/TariffElement'
last_updated:
type: string
format: date-time
TariffElement:
type: object
required: [price_components]
properties:
price_components:
type: array
items:
$ref: '#/components/schemas/PriceComponent'
restrictions:
$ref: '#/components/schemas/TariffRestrictions'
PriceComponent:
type: object
required: [type, price, step_size]
properties:
type:
type: string
description: Only ENERGY components were observed — no time or flat fees.
enum: [ENERGY]
price:
type: number
description: Price per kWh in the tariff currency.
example: 0.325
step_size:
type: integer
example: 1
TariffRestrictions:
type: object
properties:
start_time:
type: string
example: '00:00'
end_time:
type: string
example: '07:00'
day_of_week:
type: array
items:
type: string
enum: [MONDAY, TUESDAY, WEDNESDAY, THURSDAY, FRIDAY, SATURDAY, SUNDAY]
security: []