API Reference

                           ██████╗ ███████╗████████╗
                          ██╔════╝ ██╔════╝╚══██╔══╝
                          ██║  ███╗█████╗     ██║
                          ██║   ██║██╔══╝     ██║
                          ╚██████╔╝███████╗   ██║
                           ╚═════╝ ╚══════╝   ╚═╝

 ██████╗ ██████╗ ███╗   ██╗███╗   ██╗███████╗ ██████╗████████╗███████╗██████╗
██╔════╝██╔═══██╗████╗  ██║████╗  ██║██╔════╝██╔════╝╚══██╔══╝██╔════╝██╔══██╗
██║     ██║   ██║██╔██╗ ██║██╔██╗ ██║█████╗  ██║        ██║   █████╗  ██║  ██║
██║     ██║   ██║██║╚██╗██║██║╚██╗██║██╔══╝  ██║        ██║   ██╔══╝  ██║  ██║
╚██████╗╚██████╔╝██║ ╚████║██║ ╚████║███████╗╚██████╗   ██║   ███████╗██████╔╝
 ╚═════╝ ╚═════╝ ╚═╝  ╚═══╝╚═╝  ╚═══╝╚══════╝ ╚═════╝   ╚═╝   ╚══════╝╚═════╝

                 ██████╗██╗     ██╗███████╗███╗   ██╗████████╗
                ██╔════╝██║     ██║██╔════╝████╗  ██║╚══██╔══╝
                ██║     ██║     ██║█████╗  ██╔██╗ ██║   ██║
                ██║     ██║     ██║██╔══╝  ██║╚██╗██║   ██║
                ╚██████╗███████╗██║███████╗██║ ╚████║   ██║
                 ╚═════╝╚══════╝╚═╝╚══════╝╚═╝  ╚═══╝   ╚═╝

A typed Python client (and optional CLI) for Galaxy Digital’s Get Connected API

exception get_connected_client.AuthError(status_code: int, detail: str = '')[source]

Bases: GalaxyHTTPError

401/403 — bad or missing credentials.

class get_connected_client.GalaxyClient(api_key: str | None = None, base_url: str = 'https://api.galaxydigital.com/api', *, token: str | None = None, read_only: bool = False, timeout: float = 30.0, retries: int = 3)[source]

Bases: object

Entry point to the API.

All requests funnel through request(), which enforces read-only mode before anything reaches the network.

Two credentials, two jobs. The site API key (api_key, a UUID) is not an access credential: the API rejects it as an Authorization value, raw or Bearer-prefixed. Its only job is to identify the site in the body of login(). What authenticates ordinary requests is the session token (token) that login() returns – a long-lived JWT (roughly a year) sent as Authorization: Bearer <token>.

A client built with only an api_key is therefore useful for exactly one thing: calling login() to obtain a token. It is still allowed (and sends the key Bearer-prefixed, so nothing breaks for callers who have not migrated), but the server will answer 401 for anything else.

retries counts retries, not attempts: retries=3 means up to four requests (the original plus three), with exponential backoff of 0.5s, 1s and 2s between them – roughly 3.5s of sleeping in the worst case. Only idempotent methods are retried on 5xx or transport failures; a 429 is retried for every method, since a rejected request was never processed.

property read_only: bool

True when writes are forbidden, by constructor flag or the GALAXY_READ_ONLY env var.

The two sources are OR’d, never overridden: GALAXY_READ_ONLY=0 does not unblock a client constructed with read_only=True.

property http: Client

The underlying httpx.Client, a supported escape hatch.

Use it for anything request() does not model (streaming, odd content types, raw responses). It carries the same auth headers and base URL, and writes issued through it are still refused in read-only mode by the _guard() request hook – but it does not retry, unwrap envelopes, or map statuses onto exceptions.

Built lazily and cached, which is also how a fresh token takes effect: login() drops the cached transport so the next access rebuilds it around the new credential.

close() None[source]
request(method: str, path: str, *, params: dict[str, Any] | None = None, json: Any = None, treat_as_write: bool = False) Any[source]

Perform a single request, the sole gateway to the network.

Blocks writes in read-only mode before any I/O, retries with exponential backoff (honoring Retry-After on a 429), and maps error statuses onto the GalaxyHTTPError hierarchy.

A 429 is retried for every method – the request was rejected, not processed. A 5xx or a transport failure is retried only for idempotent methods; a POST or PATCH raises on the first failure rather than risk duplicating a write the server may have committed. treat_as_write also disables those retries: the whole point of the flag is that the request is not really idempotent, so repeating it could send a second email (or mint a second artifact).

Parameters:

treat_as_write – enforce the read-only guard for endpoints whose GET has side effects (e.g. /users/{id}/welcomeEmail), and suppress retries for them.

Raises:
login(user_email: str, user_password: str, key: str | None = None) LoginResult | dict[str, Any] | None[source]

Exchange credentials for a session token and start using it.

key defaults to api_key – the site key’s whole purpose. On success the returned token becomes this client’s credential: token is replaced and the cached transport is dropped, so the next request is built with Authorization: Bearer <token>.

This is a POST, so it goes through request() like any other write and is refused in read-only mode.

Raises:
  • ReadOnlyError – the client is in read-only mode. Checked before the missing-key error below: a read-only client with only a token and no site key should be told it is read-only, not that it is missing a key it was never going to use.

  • MissingAPIKeyError – no key was given and the client has no api_key to fall back on.

get_data(path: str, params: dict[str, Any] | None = None) Any[source]

GET path and return the unwrapped payload.

paginate(path: str, params: dict[str, Any] | None = None, per_page: int = 150) Iterator[dict[str, Any]][source]

Iterate all rows of a list endpoint via per_page/since_id paging.

The API answers 404 for “no results”, so that ends iteration.

exception get_connected_client.GalaxyConnectionError[source]

Bases: GalaxyError

The request never completed — DNS, TCP, TLS, or timeout failure.

exception get_connected_client.GalaxyError[source]

Bases: Exception

Base for all errors raised by this library.

exception get_connected_client.GalaxyHTTPError(status_code: int, detail: str = '')[source]

Bases: GalaxyError

An HTTP-level error response from the API.

classmethod for_status(status_code: int, detail: str = '') GalaxyHTTPError[source]
exception get_connected_client.MissingAPIKeyError[source]

Bases: GalaxyError

No API key was provided or discoverable.

exception get_connected_client.NotFoundError(status_code: int, detail: str = '')[source]

Bases: GalaxyHTTPError

404 — the API also uses this for empty list results.

exception get_connected_client.RateLimitError(status_code: int, detail: str = '')[source]

Bases: GalaxyHTTPError

429 — too many requests.

exception get_connected_client.ReadOnlyError[source]

Bases: GalaxyError

A write was attempted while the client is in read-only mode.

exception get_connected_client.ValidationFailedError(status_code: int, detail: str = '')[source]

Bases: GalaxyHTTPError

422 — the API rejected the payload.

Client

Sync HTTP client for the Galaxy Digital Get Connected API.

class get_connected_client.client.GalaxyClient(api_key: str | None = None, base_url: str = 'https://api.galaxydigital.com/api', *, token: str | None = None, read_only: bool = False, timeout: float = 30.0, retries: int = 3)[source]

Bases: object

Entry point to the API.

All requests funnel through request(), which enforces read-only mode before anything reaches the network.

Two credentials, two jobs. The site API key (api_key, a UUID) is not an access credential: the API rejects it as an Authorization value, raw or Bearer-prefixed. Its only job is to identify the site in the body of login(). What authenticates ordinary requests is the session token (token) that login() returns – a long-lived JWT (roughly a year) sent as Authorization: Bearer <token>.

A client built with only an api_key is therefore useful for exactly one thing: calling login() to obtain a token. It is still allowed (and sends the key Bearer-prefixed, so nothing breaks for callers who have not migrated), but the server will answer 401 for anything else.

retries counts retries, not attempts: retries=3 means up to four requests (the original plus three), with exponential backoff of 0.5s, 1s and 2s between them – roughly 3.5s of sleeping in the worst case. Only idempotent methods are retried on 5xx or transport failures; a 429 is retried for every method, since a rejected request was never processed.

property read_only: bool

True when writes are forbidden, by constructor flag or the GALAXY_READ_ONLY env var.

The two sources are OR’d, never overridden: GALAXY_READ_ONLY=0 does not unblock a client constructed with read_only=True.

property http: Client

The underlying httpx.Client, a supported escape hatch.

Use it for anything request() does not model (streaming, odd content types, raw responses). It carries the same auth headers and base URL, and writes issued through it are still refused in read-only mode by the _guard() request hook – but it does not retry, unwrap envelopes, or map statuses onto exceptions.

Built lazily and cached, which is also how a fresh token takes effect: login() drops the cached transport so the next access rebuilds it around the new credential.

close() None[source]
request(method: str, path: str, *, params: dict[str, Any] | None = None, json: Any = None, treat_as_write: bool = False) Any[source]

Perform a single request, the sole gateway to the network.

Blocks writes in read-only mode before any I/O, retries with exponential backoff (honoring Retry-After on a 429), and maps error statuses onto the GalaxyHTTPError hierarchy.

A 429 is retried for every method – the request was rejected, not processed. A 5xx or a transport failure is retried only for idempotent methods; a POST or PATCH raises on the first failure rather than risk duplicating a write the server may have committed. treat_as_write also disables those retries: the whole point of the flag is that the request is not really idempotent, so repeating it could send a second email (or mint a second artifact).

Parameters:

treat_as_write – enforce the read-only guard for endpoints whose GET has side effects (e.g. /users/{id}/welcomeEmail), and suppress retries for them.

Raises:
login(user_email: str, user_password: str, key: str | None = None) LoginResult | dict[str, Any] | None[source]

Exchange credentials for a session token and start using it.

key defaults to api_key – the site key’s whole purpose. On success the returned token becomes this client’s credential: token is replaced and the cached transport is dropped, so the next request is built with Authorization: Bearer <token>.

This is a POST, so it goes through request() like any other write and is refused in read-only mode.

Raises:
  • ReadOnlyError – the client is in read-only mode. Checked before the missing-key error below: a read-only client with only a token and no site key should be told it is read-only, not that it is missing a key it was never going to use.

  • MissingAPIKeyError – no key was given and the client has no api_key to fall back on.

get_data(path: str, params: dict[str, Any] | None = None) Any[source]

GET path and return the unwrapped payload.

paginate(path: str, params: dict[str, Any] | None = None, per_page: int = 150) Iterator[dict[str, Any]][source]

Iterate all rows of a list endpoint via per_page/since_id paging.

The API answers 404 for “no results”, so that ends iteration.

Exceptions

Exception hierarchy for the Galaxy Digital API client.

exception get_connected_client.exceptions.GalaxyError[source]

Bases: Exception

Base for all errors raised by this library.

exception get_connected_client.exceptions.MissingAPIKeyError[source]

Bases: GalaxyError

No API key was provided or discoverable.

exception get_connected_client.exceptions.ReadOnlyError[source]

Bases: GalaxyError

A write was attempted while the client is in read-only mode.

exception get_connected_client.exceptions.GalaxyConnectionError[source]

Bases: GalaxyError

The request never completed — DNS, TCP, TLS, or timeout failure.

exception get_connected_client.exceptions.GalaxyHTTPError(status_code: int, detail: str = '')[source]

Bases: GalaxyError

An HTTP-level error response from the API.

classmethod for_status(status_code: int, detail: str = '') GalaxyHTTPError[source]
exception get_connected_client.exceptions.AuthError(status_code: int, detail: str = '')[source]

Bases: GalaxyHTTPError

401/403 — bad or missing credentials.

exception get_connected_client.exceptions.NotFoundError(status_code: int, detail: str = '')[source]

Bases: GalaxyHTTPError

404 — the API also uses this for empty list results.

exception get_connected_client.exceptions.ValidationFailedError(status_code: int, detail: str = '')[source]

Bases: GalaxyHTTPError

422 — the API rejected the payload.

exception get_connected_client.exceptions.RateLimitError(status_code: int, detail: str = '')[source]

Bases: GalaxyHTTPError

429 — too many requests.

Configuration

Settings resolution: explicit args > env vars > defaults.

There is no configuration file. Anything the CLI does not receive as an explicit flag comes from GALAXY_API_KEY, GALAXY_API_TOKEN, GALAXY_API_URL or GALAXY_READ_ONLY, and failing those from the built-in defaults (server us1, read-only off, no credentials).

The two credentials are not interchangeable: GALAXY_API_KEY is the site key, which only ever identifies the site in a login body, while GALAXY_API_TOKEN is the session token galaxy auth login mints and the only thing that authenticates a request.

get_connected_client.config.parse_bool(value: str) bool[source]

Coerce a string to a boolean by membership in the truthy set.

get_connected_client.config.env_read_only() bool | None[source]

Read the GALAXY_READ_ONLY env var as a tri-state boolean.

get_connected_client.config.resolve_url(url: str) str[source]

Resolve a server alias (us1/us2/ca) to its full URL, or pass through.

class get_connected_client.config.Settings(api_key: str | None, url: str, read_only: bool, token: str | None = None)[source]

Bases: object

Resolved settings for the Galaxy Digital API client.

token defaults to None so callers constructing a Settings positionally keep working; it is the session credential, api_key the site key used to log in.

api_key: str | None
url: str
read_only: bool
token: str | None = None
get_connected_client.config.load_settings(api_key: str | None = None, url: str | None = None, read_only: bool | None = None, token: str | None = None) Settings[source]

Resolve settings with precedence: explicit args > env vars > defaults.

token resolves from the argument, then GALAXY_API_TOKEN, then None – the same shape as api_key and GALAXY_API_KEY.

Resources

Base classes

Declarative plumbing shared by all resource namespaces.

class get_connected_client.resources.base.Resource(client: GalaxyClient)[source]

Bases: Generic[M]

Base for a resource namespace: one API endpoint and its model.

Subclasses declare two attributes and inherit whichever CRUD mixins the endpoint supports:

  • path – the endpoint’s path relative to the API root, e.g. "/users". It is the base for every URL the namespace builds.

  • model – the GalaxyModel subclass rows of this endpoint validate into. It is also the type parameter, so the mixins’ return types stay precise:

    class Users(ListMixin[User], GetMixin[User], Resource[User]):
        path = "/users"
        model = User
    

Users(client).get(5) then types as User, not GalaxyModel.

model is deliberately not a ClassVar: a ClassVar may not reference a type variable.

path: ClassVar[str]
model: type[M]
url(*parts: Any) str[source]

Public path builder – use for confirm prompts so they can’t drift from the wire.

With no parts this is the collection itself, self.path.

class get_connected_client.resources.base.ListMixin(client: GalaxyClient)[source]

Bases: Resource[M]

Adds list() to a namespace whose endpoint is paginated.

list(*, per_page: int = 150, since_id: int | None = None, since_created: str | None = None, since_updated: str | None = None, show_inactive: bool | None = None, **filters: Any) Iterator[M][source]

Iterate every row of the endpoint, paging transparently.

Rows stream as they arrive; the iterator issues one request per page and stops when the server runs out of rows.

Parameters:
  • per_page – rows per request, clamped by the client to the API maximum of MAX_PER_PAGE. Tunes request count, not results.

  • since_id – return only rows with an id greater than this. The client also uses it as the paging cursor.

  • since_created – server-side filter on creation time, formatted "YYYY-MM-DD HH:MM".

  • since_updated – server-side filter on last-modified time, same format as since_created.

  • show_inactiveTrue sends "Yes" and False sends "No"; None (the default) omits the parameter entirely and takes the server default, which excludes inactive records.

  • filters – any further endpoint-specific query parameters, passed through verbatim. None values are dropped.

Returns:

an iterator of model instances.

class get_connected_client.resources.base.GetMixin(client: GalaxyClient)[source]

Bases: Resource[M]

Adds get() to a namespace whose endpoint serves single rows.

get(id: int) M[source]

Fetch the row with this id.

Raises:

NotFoundError – no such row.

Returns:

the parsed model instance.

class get_connected_client.resources.base.CreateMixin(client: GalaxyClient)[source]

Bases: Resource[M]

Adds create() to a namespace whose endpoint accepts POSTs.

create(**fields: Any) M | dict[str, Any] | None[source]

POST fields to the endpoint to create a row.

Parameters:

fields – the new row’s attributes, sent as the JSON body.

Raises:

ReadOnlyError – the client is in read-only mode.

Returns:

the parsed model when the API returns a data object; otherwise the raw response payload, since some endpoints return nothing or a bare message.

class get_connected_client.resources.base.UpdateMixin(client: GalaxyClient)[source]

Bases: Resource[M]

Adds update() to a namespace whose endpoint accepts PUTs.

update(id: int, **fields: Any) M | dict[str, Any] | None[source]

PUT fields to the row with this id.

Only the supplied fields are sent, so this is a partial update.

Parameters:
  • id – the row to modify.

  • fields – the attributes to change, sent as the JSON body.

Raises:

ReadOnlyError – the client is in read-only mode.

Returns:

the parsed model when the API returns a data object; otherwise the raw response payload, since some endpoints return nothing or a bare message.

class get_connected_client.resources.base.DeleteMixin(client: GalaxyClient)[source]

Bases: Resource[M]

Adds delete() to a namespace whose endpoint accepts DELETEs.

delete(id: int) None[source]

Delete the row with this id.

Raises:

Agencies

The /agencies namespace: CRUD plus every agency sub-resource.

class get_connected_client.resources.agencies.Agencies(client: GalaxyClient)[source]

Bases: ListMixin[Agency], GetMixin[Agency], CreateMixin[Agency], UpdateMixin[Agency], DeleteMixin[Agency], Resource[Agency]

Agencies and everything hanging off them.

This namespace covers every /agencies endpoint in doc/api.yml – 10 of 10 paths, 17 of 17 operations, full coverage, nothing excluded. They group as:

  • CRUD on the collection and the row – list(), get(), create(), update(), delete(), inherited from the mixins.

  • Membership sub-resources, each a read plus add/remove – causes(), clusters(), managers() and tags().

list() accepts the endpoint’s standard paging filters – see list()/agencies defines no filters of its own beyond those.

path: ClassVar[str] = '/agencies'
model

alias of Agency

causes(id: int) list[Cause][source]

The causes attached to this agency.

add_cause(id: int, cause_id: int) Any[source]

Attach cause_id to this agency.

remove_cause(id: int, cause_id: int) Any[source]

Detach cause_id from this agency.

clusters(id: int) list[Cluster][source]

The clusters attached to this agency.

add_cluster(id: int, cluster_id: int) Any[source]

Attach cluster_id to this agency.

remove_cluster(id: int, cluster_id: int) Any[source]

Detach cluster_id from this agency.

managers(id: int) list[UserMini][source]

The users who manage this agency.

add_manager(id: int, user_id: int) Any[source]

Make user_id a manager of this agency.

remove_manager(id: int, user_id: int) Any[source]

Remove user_id as a manager of this agency.

tags(id: int) list[Tag][source]

The tags on this agency.

add_tags(id: int, tags: list[str]) Any[source]

Add tags – names, not ids – to this agency.

remove_tag(id: int, tag_id: int) Any[source]

Remove the tag with this id from the agency.

Auth

The credential-exchange namespace: /users/login and /users/authenticate – the pair Users deliberately leaves out.

class get_connected_client.resources.auth.Auth(client: GalaxyClient)[source]

Bases: Resource[LoginResult]

Credential exchange, covering the two paths Users excludes.

2 of 2 paths, 2 of 2 operations, full coverage of the pair. Combined with Users’s 21 of 23, the API is now covered end to end – 66 of 66 paths across the whole client.

Both login() and authenticate() are POSTs and so pass through the client’s ordinary read-only choke point: client.request refuses every write when the client is in read-only mode, and login/authenticate are no exception – a login mints a bearer token, which is a side effect worth gating even though it changes nothing about a stored record. --read-only therefore blocks both commands on the CLI just as it blocks create/update/delete elsewhere.

path: ClassVar[str] = '/users'
model

alias of LoginResult

login(user_email: str, user_password: str, key: str | None = None) LoginResult | dict[str, Any] | None[source]

Exchange credentials (and the site key) for a session token.

The spec marks key required, and the API means it – the body is validated before authentication, so a missing key is a 422 rather than a 401. None (the default) therefore falls back to the client’s api_key, which is what that key exists for.

Prefer login(): it does the same exchange and then adopts the token, so subsequent requests authenticate. This method only returns it.

Returns:

a LoginResult when the API answers with a data object; otherwise the raw response payload, mirroring create().

Raises:

MissingAPIKeyError – no key was given and the client has no api_key to fall back on.

authenticate(user_email: str, user_password: str) list[UserOneclick][source]

Verify credentials and mint a one-click login link.

The spec has data answer with an array of UserOneclick rows rather than a bare object – confirmed against doc/api.yml’s authenticateResponse.

Benchmarks

The /benchmarks namespace: full CRUD plus the users sub-list.

class get_connected_client.resources.benchmarks.Benchmarks(client: GalaxyClient)[source]

Bases: ListMixin[Benchmark], GetMixin[Benchmark], CreateMixin[Benchmark], UpdateMixin[Benchmark], DeleteMixin[Benchmark], Resource[Benchmark]

Benchmarks – service milestones volunteers can earn.

This namespace covers every /benchmarks endpoint in doc/api.yml – 3 of 3 paths, 6 of 6 operations, full coverage. They group as:

  • CRUDlist(), get(), create(), update(), delete(), inherited from the mixins.

  • Membershipusers(), the volunteers who have earned this benchmark. The spec answers with userMiniObject rows, not the full benchmarkMiniObject-flavored user – confirmed against doc/api.yml’s listBenchmarkUsersResponse.

path: ClassVar[str] = '/benchmarks'
model

alias of Benchmark

users(id: int) list[UserMini][source]

The users who have earned this benchmark.

Events

The /events namespace: plain CRUD, no sub-resources.

class get_connected_client.resources.events.Events(client: GalaxyClient)[source]

Bases: ListMixin[Event], GetMixin[Event], CreateMixin[Event], UpdateMixin[Event], DeleteMixin[Event], Resource[Event]

Agency events.

This namespace covers every /events endpoint in doc/api.yml – 2 of 2 paths, 5 of 5 operations, full coverage. There are no sub-resources: just CRUD on the collection and the row – list(), get(), create(), update(), delete(), inherited from the mixins.

Note

Unlike most other list endpoints, /events does not accept show_inactive – the spec’s listEvents operation only takes per_page, since_id, since_created and since_updated. list() still inherits the parameter from ListMixin, but passing it has no effect on the server; the CLI does not expose it for this resource.

path: ClassVar[str] = '/events'
model

alias of Event

Groups

The /groups namespace: CRUD plus needs/users membership.

class get_connected_client.resources.groups.Groups(client: GalaxyClient)[source]

Bases: ListMixin[Group], GetMixin[Group], CreateMixin[Group], UpdateMixin[Group], DeleteMixin[Group], Resource[Group]

User groups and everything hanging off them.

This namespace covers every /groups endpoint in doc/api.yml – 4 of 4 paths, 9 of 9 operations, full coverage, nothing excluded. They group as:

  • CRUD on the collection and the row – list(), get(), create(), update(), delete(), inherited from the mixins.

  • Membership, add/remove only (the API has no dedicated read endpoint for either – both live on the needs/users arrays of the group object itself) – add_need()/remove_need() and add_user()/remove_user().

list() accepts show_inactive in addition to the standard paging filters – see list().

path: ClassVar[str] = '/groups'
model

alias of Group

add_need(id: int, need_id: int) Any[source]

Attach need_id to this group.

remove_need(id: int, need_id: int) Any[source]

Detach need_id from this group.

add_user(id: int, user_id: int) Any[source]

Attach user_id to this group.

remove_user(id: int, user_id: int) Any[source]

Detach user_id from this group.

Hours

The /hours namespace: plain CRUD, no sub-resources.

class get_connected_client.resources.hours.Hours(client: GalaxyClient)[source]

Bases: ListMixin[Hour], GetMixin[Hour], CreateMixin[Hour], UpdateMixin[Hour], DeleteMixin[Hour], Resource[Hour]

Volunteer hour records.

This namespace covers every /hours endpoint in doc/api.yml – 2 of 2 paths, 5 of 5 operations, full coverage. There are no sub-resources: just CRUD on the collection and the row – list(), get(), create(), update(), delete(), inherited from the mixins.

Unlike /events, /hours list does accept show_inactive:

client.hours.list(show_inactive=True)
path: ClassVar[str] = '/hours'
model

alias of Hour

Misc (clusters, lookups)

The /clusters namespace, plus the site’s read-only lookup lists.

Clusters is a small CRUD-minus-two namespace (agencies attach to clusters; see clusters()). Lookups bundles four unrelated flat GET-only endpoints – /causes, /interests, /impacts and /questions/registration – that share no {id} and no request shape, only the fact that each is a fixed list the site defines up front.

class get_connected_client.resources.misc.Clusters(client: GalaxyClient)[source]

Bases: ListMixin[Cluster], CreateMixin[Cluster], DeleteMixin[Cluster], Resource[Cluster]

Clusters – named groupings agencies attach to.

This namespace covers every /clusters endpoint in doc/api.yml – 2 of 2 paths, 3 of 3 operations, full coverage. There is no GetMixin/UpdateMixin: the spec defines neither GET /clusters/{id} nor PUT /clusters/{id}.

GET /clusters declares no query parameters at all in the spec – not even the usual paging trio per_page/since_id/since_created – unlike every other list endpoint in this API. list() still accepts them, for the same call signature as every other namespace; any unrecognized parameter is simply not documented as doing anything.

path: ClassVar[str] = '/clusters'
model

alias of Cluster

class get_connected_client.resources.misc.Lookups(client: GalaxyClient)[source]

Bases: Resource[Cause]

Read-only site-wide lookups, each with no {id} of its own.

Covers /causes, /interests, /impacts and /questions/registration – 4 of 4 paths, 4 of 4 operations, full coverage. path/model are unused placeholders required by Resource: each method below names its own endpoint and return model directly, since the four endpoints have nothing in common but being flat, unpaginated, GET-only lists.

path: ClassVar[str] = ''
model

alias of Cause

causes() list[Cause][source]

The site’s available causes.

interests() list[Interest][source]

The site’s available interests.

impacts() list[Impact][source]

The site’s available impact areas.

registration_questions() list[Question][source]

The site’s custom registration questions.

Needs

The /needs namespace: CRUD plus every need sub-resource.

class get_connected_client.resources.needs.Needs(client: GalaxyClient)[source]

Bases: ListMixin[Need], GetMixin[Need], CreateMixin[Need], UpdateMixin[Need], DeleteMixin[Need], Resource[Need]

Needs (volunteer opportunities) and everything hanging off them.

This namespace covers every /needs endpoint in doc/api.yml – 8 of 8 paths, 13 of 13 operations, full coverage, nothing excluded. They group as:

list() accepts the endpoint’s own filters on top of the standard paging ones:

client.needs.list(agency_id=9, need_status="active")

Supported filters: agency_id, need_title and need_status.

Note

/needs/{id}/shifts does not use shiftRequestSchema (that schema’s slots/start_date/start_time/duration fields are only used inside needRequestSchema’s embedded shifts array, i.e. when shifts are supplied as part of a need create/update). The dedicated endpoint has its own inline schema instead: a shifts array of {"start", "slots", "duration"} objects, with one combined start datetime rather than a separate date/time pair. add_shift() keeps the friendlier separate start_date/start_time arguments and joins them into start to match what the endpoint actually expects on the wire.

path: ClassVar[str] = '/needs'
model

alias of Need

responses(id: int) list[Response][source]

The responses (sign-ups) to this need.

add_shift(id: int, *, slots: int, start_date: str, start_time: str, duration: str) Any[source]

Add a shift to this need.

See the class docstring’s note: the wire body is {"shifts": [{"start": ..., "slots": ..., "duration": ...}]}, not the four flat fields of shiftRequestSchema. start_date and start_time are joined with a space to build start.

remove_shift(id: int, shift_id: int) Any[source]

Remove shift_id from this need.

add_interest(id: int, interest_id: int) Any[source]

Attach interest_id to this need.

remove_interest(id: int, interest_id: int) Any[source]

Detach interest_id from this need.

add_qualification(id: int, qualification_id: int) Any[source]

Attach qualification_id to this need.

remove_qualification(id: int, qualification_id: int) Any[source]

Detach qualification_id from this need.

questions(id: int) list[Question][source]

The custom questions asked of volunteers responding to this need.

Qualifications

The /qualifications namespace: full CRUD plus the users sub-list.

class get_connected_client.resources.qualifications.Qualifications(client: GalaxyClient)[source]

Bases: ListMixin[Qualification], GetMixin[Qualification], CreateMixin[Qualification], UpdateMixin[Qualification], DeleteMixin[Qualification], Resource[Qualification]

Qualifications – credentials a volunteer can hold or be asked for.

This namespace covers every /qualifications endpoint in doc/api.yml – 3 of 3 paths, 6 of 6 operations, full coverage. They group as:

  • CRUDlist(), get(), create(), update(), delete(), inherited from the mixins.

  • Membershipusers(), the volunteers who hold this qualification.

path: ClassVar[str] = '/qualifications'
model

alias of Qualification

users(id: int) list[QualificationUser][source]

The users who hold this qualification.

Responses

The /responses namespace: plain CRUD, no sub-resources.

class get_connected_client.resources.responses.Responses(client: GalaxyClient)[source]

Bases: ListMixin[Response], GetMixin[Response], CreateMixin[Response], UpdateMixin[Response], DeleteMixin[Response], Resource[Response]

Volunteer responses (sign-ups) to needs.

This namespace covers every /responses endpoint in doc/api.yml – 2 of 2 paths, 5 of 5 operations, full coverage. There are no sub-resources: just CRUD on the collection and the row – list(), get(), create(), update(), delete(), inherited from the mixins.

list() accepts show_inactive in addition to the standard paging filters – see list():

client.responses.list(show_inactive=True)
path: ClassVar[str] = '/responses'
model

alias of Response

Teams

The /teams namespace: list/get/create/delete plus membership.

class get_connected_client.resources.teams.Teams(client: GalaxyClient)[source]

Bases: ListMixin[Team], GetMixin[Team], CreateMixin[Team], DeleteMixin[Team], Resource[Team]

Teams – a group of volunteers responding together to a single need.

This namespace covers every /teams endpoint in doc/api.yml – 3 of 3 paths, 6 of 6 operations, full coverage, nothing excluded. They group as:

  • CRUD, minus update – list(), get(), create(), delete(), inherited from the mixins. There is no UpdateMixin: the spec defines no PUT /teams/{id}.

  • Membershipadd_member()/remove_member().

list() accepts show_inactive in addition to the standard paging filters – see list().

path: ClassVar[str] = '/teams'
model

alias of Team

add_member(id: int, member: int, *, sch_id: int | None = None) Any[source]

Attach member (a user id) to this team.

sch_id – a schedule id – is the one optional field of the spec’s teamMemberAttachRequest body; omitted, an empty JSON object is still sent since the endpoint marks the body required.

remove_member(id: int, member: int) Any[source]

Detach member (a user id) from this team.

Users

The /users namespace: CRUD plus every user sub-resource.

class get_connected_client.resources.users.Users(client: GalaxyClient)[source]

Bases: ListMixin[User], GetMixin[User], CreateMixin[User], UpdateMixin[User], DeleteMixin[User], Resource[User]

Users and everything hanging off them.

This namespace covers every /users endpoint in doc/api.yml except the credential-exchange pair – /users/authenticate and /users/login – which live on Auth instead: 21 of 23 paths, 32 of 34 operations, one method apiece. Rather than enumerate the rest here (a list that rots the moment one is added), they group as:

list() accepts the endpoint’s own filters on top of the standard paging ones:

client.users.list(user_status="active", user_email_like="@example.com")

Supported filters: user_status, user_fname, user_lname, user_email, user_fname_like, user_lname_like and user_email_like.

path: ClassVar[str] = '/users'
model

alias of User

agencies(id: int) list[AgencyMini][source]

The agencies this user has fanned.

add_agency(id: int, agency_id: int) Any[source]

Fan agency_id on behalf of this user.

remove_agency(id: int, agency_id: int) Any[source]

Drop this user’s fan relationship with agency_id.

benchmarks(id: int) list[BenchmarkMini][source]

The benchmarks (service milestones) this user has earned.

remove_benchmark(id: int, benchmark_id: int) Any[source]

Take benchmark_id away from this user.

causes(id: int) list[Cause][source]

The causes this user cares about.

add_cause(id: int, cause_id: int) Any[source]

Assign cause_id to this user.

remove_cause(id: int, cause_id: int) Any[source]

Unassign cause_id from this user.

extras(id: int, subset: str | None = None) list[Extra][source]

This user’s custom key/value data.

Parameters:

subset"regExtra" (the server default) or "profile".

Returns:

the stored pairs, or [] when the user has none – the API answers 404 rather than an empty list.

set_extras(id: int, extras: list[dict[str, Any]] | dict[str, Any], subset: str | None = None) Any[source]

Replace this user’s extras with extras.

The spec’s shape is {"extras": [{"key": ..., "value": ...}, ...]}. The payload is the entirety of the user’s extras for the subset, so an update must resend the pairs it wants to keep.

Parameters:
  • extras – either the bare [{"key": ..., "value": ...}, ...] list – wrapped in the {"extras": ...} envelope for you – or a dict that already contains that envelope, sent verbatim.

  • subset"regExtra" (the server default) or "profile".

hours(id: int) list[Hour][source]

The volunteer hours this user has submitted.

interests(id: int) list[Interest][source]

The interests assigned to this user.

add_interest(id: int, interest_id: int) Any[source]

Assign interest_id to this user.

remove_interest(id: int, interest_id: int) Any[source]

Unassign interest_id from this user.

send_welcome_email(id: int) Any[source]

Send this user the site’s welcome email.

A GET with a side effect: the spec models it as a read, but it puts mail in someone’s inbox. Treat it as a write.

oneclick(id: int) UserOneclick[source]

Mint a one-click (passwordless) login link for this user.

A GET with a side effect: it issues a credential, so it is treated as a write and refused in read-only mode (see the note above this method).

Raises:

ReadOnlyError – the client is in read-only mode.

optouts(id: int) UserOptouts[source]

The message areas this user has opted out of.

Raises:

NotFoundError – the user has not opted out of anything.

add_optout(id: int, optout_areas: list[str]) Any[source]

Opt this user out of messaging.

Parameters:

optout_areas

area names, or ["all"]. The list supersedes whatever was stored before:

client.users.add_optout(5, ["blast"])

remove_optout(id: int, optout_areas: list[str]) Any[source]

Remove areas from this user’s opt-out list.

Parameters:

optout_areas – unlike add_optout(), this names only the areas to lift, leaving the rest of the opt-outs in place.

qualifications(id: int) list[UserQualification][source]

The qualifications this user holds.

registration_answers(id: int) list[RegistrationAnswer][source]

This user’s answers to the site’s custom registration questions.

set_registration_answers(id: int, answers: list[dict[str, Any]]) Any[source]

Store this user’s answers to the custom registration questions.

Parameters:

answers – the spec’s answers array – objects of {"question_id": ..., "answer": [...]}. It is wrapped in the required {"answers": ...} envelope for you.

responses(id: int) list[UserResponse][source]

The needs this user has signed up for.

tracks(id: int) list[TrackMini][source]

The tracks this user belongs to.

tags(id: int) list[Tag][source]

The tags on this user.

add_tags(id: int, tags: list[str]) Any[source]

Add tags – names, not ids – to this user.

remove_tag(id: int, tag_id: int) Any[source]

Remove the tag with this id from the user.

Models

Base

Base model preserving unknown fields (the API schema is loose).

class get_connected_client.models.base.GalaxyModel(**extra_data: Any)[source]

Bases: BaseModel

Base for all Galaxy Digital API models.

The Get Connected API returns loose data - ids are sometimes strings, responses may include fields not documented in the OpenAPI spec, and integer fields occasionally arrive as "" or non-numeric strings. This base preserves unknown fields so round-tripping through model_dump() does not silently drop data, and degrades unparseable numerics to None instead of refusing the whole record.

model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

Common

Small shared models used across Galaxy Digital API resources.

Each class corresponds to a schema in components.schemas of the vendored OpenAPI spec (doc/api.yml). Field names match the spec verbatim. The API represents numeric ids as strings; pydantic coerces those to int on validation.

class get_connected_client.models.common.Tag(*, id: int | None = None, name: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

tagObject.

id: int | None
name: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.Cause(*, id: int | None = None, name: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

causeObject.

id: int | None
name: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.Cluster(*, id: int | None = None, name: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

clusterObject.

id: int | None
name: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.Interest(*, id: int | None = None, name: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

interestObject.

id: int | None
name: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.Impact(*, id: int | None = None, impact_name: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

impactObject.

id: int | None
impact_name: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.Category(*, id: int | None = None, name: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

categoryObject.

id: int | None
name: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.Extra(*, key: str | None = None, value: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

extraObject.

key: str | None
value: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.Question(*, id: int | None = None, q_type: str | None = None, q_label: str | None = None, q_options: list[str] | None = None, q_area: str | None = None, q_area_id: int | None = None, q_status: str | None = None, created_at: str | None = None, updated_at: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

questionObject.

id: int | None
q_type: str | None
q_label: str | None
q_options: list[str] | None
q_area: str | None
q_area_id: int | None
q_status: str | None
created_at: str | None
updated_at: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.Shift(*, id: int | None = None, start: str | None = None, end: str | None = None, duration: str | None = None, slots: int | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

shiftObject.

id: int | None
start: str | None
end: str | None
duration: str | None
slots: int | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.TrackMini(*, id: int | None = None, name: str | None = None, created_at: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

trackMiniObject.

id: int | None
name: str | None
created_at: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.BenchmarkMini(*, id: int | None = None, benchmark_status: str | None = None, benchmark_title: str | None = None, benchmark_icon: str | None = None, benchmark_hours: str | None = None, benchmark_date_start: str | None = None, benchmark_date_end: str | None = None, created_at: str | None = None, update_at: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

benchmarkMiniObject.

update_at is spelled that way in the spec – the API’s own typo, kept verbatim so payloads round-trip.

id: int | None
benchmark_status: str | None
benchmark_title: str | None
benchmark_icon: str | None
benchmark_hours: str | None
benchmark_date_start: str | None
benchmark_date_end: str | None
created_at: str | None
update_at: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.UserMini(*, id: int | None = None, domain_id: int | None = None, user_fname: str | None = None, user_lname: str | None = None, user_email: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

userMiniObject.

id: int | None
domain_id: int | None
user_fname: str | None
user_lname: str | None
user_email: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.AgencyMini(*, id: int | None = None, domain_id: int | None = None, agency_name: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

agencyMiniObject.

id: int | None
domain_id: int | None
agency_name: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.NeedMini(*, id: int | None = None, domain_id: int | None = None, need_title: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

needMiniObject.

id: int | None
domain_id: int | None
need_title: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.GroupMini(*, id: int | None = None, domain_id: int | None = None, group_title: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

groupMiniObject.

id: int | None
domain_id: int | None
group_title: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.InitiativeMini(*, id: int | None = None, domain_id: int | None = None, init_title: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

initiativeMiniObject.

id: int | None
domain_id: int | None
init_title: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.common.TeamMini(*, id: int | None = None, domain_id: int | None = None, team_name: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

teamMiniObject.

id: int | None
domain_id: int | None
team_name: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

Agencies

Models for the /agencies endpoints.

Field names are copied verbatim from doc/api.yml; the API sends numeric ids as strings and pydantic coerces them.

class get_connected_client.models.agencies.Agency(*, id: int | None = None, domain_id: int | None = None, agency_name: str | None = None, agency_link: str | None = None, agency_address: str | None = None, agency_address2: str | None = None, agency_city: str | None = None, agency_state: str | None = None, agency_postal: str | None = None, agency_extra_location: str | None = None, agency_phone: str | None = None, agency_phone_extension: str | None = None, agency_fax: str | None = None, agency_twitter_link: str | None = None, agency_facebook_link: str | None = None, agency_instagram_link: str | None = None, agency_youtube_link: str | None = None, agency_linkedin_link: str | None = None, agency_email: str | None = None, agency_video: str | None = None, agency_url: str | None = None, agency_ein: str | None = None, agency_comments: str | None = None, agency_status: str | None = None, agency_latitude: str | None = None, agency_longitude: str | None = None, agency_contact: str | None = None, agency_contact_title: str | None = None, agency_news: str | None = None, agency_mission: str | None = None, agency_contacts: list[str] | None = None, agency_hours: str | None = None, agency_partner: str | None = None, logo: str | None = None, created_at: str | None = None, updated_at: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

agencyObject – an organization on the site.

id: int | None
domain_id: int | None
agency_name: str | None
agency_address: str | None
agency_address2: str | None
agency_city: str | None
agency_state: str | None
agency_postal: str | None
agency_extra_location: str | None
agency_phone: str | None
agency_phone_extension: str | None
agency_fax: str | None
agency_email: str | None
agency_video: str | None
agency_url: str | None
agency_ein: str | None
agency_comments: str | None
agency_status: str | None
agency_latitude: str | None
agency_longitude: str | None
agency_contact: str | None
agency_contact_title: str | None
agency_news: str | None
agency_mission: str | None
agency_contacts: list[str] | None
agency_hours: str | None
agency_partner: str | None
created_at: str | None
updated_at: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

Auth

Models for the credential-exchange endpoints.

/users/authenticate answers with an array of UserOneclick rows directly, so it needs no model of its own here – only /users/login’s response shape, loginObject, does.

class get_connected_client.models.auth.LoginResult(*, user: User | None = None, token: str | None = None, expires: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

loginObject – the outcome of POST /users/login.

user is typed as the full User model even though the spec’s nested object documents only five of its fields – every User field is optional, so the smaller payload parses cleanly and callers get the same shape as client.users.get.

user: User | None
token: str | None
expires: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

Benchmarks

Models for the /benchmarks endpoints.

Field names are copied verbatim from doc/api.yml; the API sends numeric ids as strings and pydantic coerces them.

class get_connected_client.models.benchmarks.Benchmark(*, id: int | None = None, benchmark_status: str | None = None, benchmark_title: str | None = None, benchmark_icon: str | None = None, benchmark_hours: str | None = None, benchmark_date_start: str | None = None, benchmark_date_end: str | None = None, benchmark_approval_required: str | None = None, benchmark_allow_indv_hours: str | None = None, benchmark_group_id: int | None = None, created_at: str | None = None, update_at: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

benchmarkObject – a service milestone volunteers can earn.

update_at is spelled that way in the spec – the API’s own typo, kept verbatim so payloads round-trip (see also BenchmarkMini, which carries the same typo).

id: int | None
benchmark_status: str | None
benchmark_title: str | None
benchmark_icon: str | None
benchmark_hours: str | None
benchmark_date_start: str | None
benchmark_date_end: str | None
benchmark_approval_required: str | None
benchmark_allow_indv_hours: str | None
benchmark_group_id: int | None
created_at: str | None
update_at: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

Events

Models for the /events endpoints.

Field names are copied verbatim from doc/api.yml; the API sends numeric ids as strings and pydantic coerces them.

class get_connected_client.models.events.Event(*, id: int | None = None, domain_id: int | None = None, event_area: str | None = None, event_area_id: int | None = None, event_title: str | None = None, event_description: str | None = None, event_location: str | None = None, event_address: str | None = None, event_address2: str | None = None, event_city: str | None = None, event_state: str | None = None, event_postal: str | None = None, event_email: str | None = None, event_rsvp: str | None = None, event_date_start: str | None = None, event_date_end: str | None = None, event_all_day: str | None = None, event_comments: str | None = None, tags: list[Tag] | None = None, created_at: str | None = None, update_at: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

eventObject – an agency event.

update_at is spelled that way in the spec – the API’s own typo (see also benchmarkMiniObject), kept verbatim so payloads round-trip.

id: int | None
domain_id: int | None
event_area: str | None
event_area_id: int | None
event_title: str | None
event_description: str | None
event_location: str | None
event_address: str | None
event_address2: str | None
event_city: str | None
event_state: str | None
event_postal: str | None
event_email: str | None
event_rsvp: str | None
event_date_start: str | None
event_date_end: str | None
event_all_day: str | None
event_comments: str | None
tags: list[Tag] | None
created_at: str | None
update_at: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

Groups

Models for the /groups endpoints.

Field names are copied verbatim from doc/api.yml; the API sends numeric ids as strings and pydantic coerces them.

class get_connected_client.models.groups.GroupUser(*, id: int | None = None, domain_id: int | None = None, user_fname: str | None = None, user_lname: str | None = None, user_email: str | None = None, leader: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

GroupUserMiniObject – one user attached to a user group.

id: int | None
domain_id: int | None
user_fname: str | None
user_lname: str | None
user_email: str | None
leader: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.groups.Group(*, id: int | None = None, domain_id: int | None = None, ug_status: str | None = None, ug_title: str | None = None, ug_description: str | None = None, ug_description_private: str | None = None, ug_domains: str | None = None, ug_color: str | None = None, ug_text_color: str | None = None, ug_icon: str | None = None, ug_suppress_resume: str | None = None, ug_allow_member_remove: str | None = None, ug_submitted_hours: str | None = None, ug_block_id: str | None = None, ug_limit: str | None = None, ug_goal: str | None = None, ug_approval: str | None = None, created_at: str | None = None, updated_at: str | None = None, needs: list[NeedMini] | None = None, users: list[GroupUser] | None = None, agencies: list[AgencyMini] | None = None, questions_reflection: list[Question] | None = None, questions_join: list[Question] | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

groupObject – a user group.

Called “team” in some Get Connected UI copy, but this is a distinct resource from teamObject/Team.

id: int | None
domain_id: int | None
ug_status: str | None
ug_title: str | None
ug_description: str | None
ug_description_private: str | None
ug_domains: str | None
ug_color: str | None
ug_text_color: str | None
ug_icon: str | None
ug_suppress_resume: str | None
ug_allow_member_remove: str | None
ug_submitted_hours: str | None
ug_block_id: str | None
ug_limit: str | None
ug_goal: str | None
ug_approval: str | None
created_at: str | None
updated_at: str | None
needs: list[NeedMini] | None
users: list[GroupUser] | None
agencies: list[AgencyMini] | None
questions_reflection: list[Question] | None
questions_join: list[Question] | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

Hours

Models for volunteer hour records (hourObject).

class get_connected_client.models.hours.Hour(*, id: int | None = None, domain_id: int | None = None, user: UserMini | None = None, groups: list[GroupMini] | None = None, need: NeedMini | None = None, hour_description: str | None = None, hour_date_start: str | None = None, hour_date_end: str | None = None, hour_hours: str | None = None, hour_miles: str | None = None, hour_location: str | None = None, hour_contact_name: str | None = None, hour_contact_details: str | None = None, hour_relationship: str | None = None, hour_parent: str | None = None, hour_source: str | None = None, hour_status: str | None = None, hour_type: str | None = None, created_at: str | None = None, updated_at: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

hourObject – one submitted block of volunteer time.

id: int | None
domain_id: int | None
user: UserMini | None
groups: list[GroupMini] | None
need: NeedMini | None
hour_description: str | None
hour_date_start: str | None
hour_date_end: str | None
hour_hours: str | None
hour_miles: str | None
hour_location: str | None
hour_contact_name: str | None
hour_contact_details: str | None
hour_relationship: str | None
hour_parent: str | None
hour_source: str | None
hour_status: str | None
hour_type: str | None
created_at: str | None
updated_at: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

Needs

Models for the /needs endpoints.

Field names are copied verbatim from doc/api.yml; the API sends numeric ids as strings and pydantic coerces them.

class get_connected_client.models.needs.Need(*, id: int | None = None, domain_id: int | None = None, agency: AgencyMini | None = None, initiative: InitiativeMini | None = None, groups: list[GroupMini] | None = None, need_title: str | None = None, need_body: str | None = None, need_address: str | None = None, need_address2: str | None = None, need_city: str | None = None, need_state: str | None = None, need_postal: str | None = None, need_type: str | None = None, need_contact: str | None = None, need_response_notify: str | None = None, need_date: str | None = None, need_date_type: str | None = None, need_impact_area: str | None = None, need_volunteers_needed: str | None = None, need_public: str | None = None, need_allow_groups: str | None = None, need_hours: str | None = None, need_comments: str | None = None, need_latitude: str | None = None, need_longitude: str | None = None, need_date_close: str | None = None, family_friendly: str | None = None, outdoors: str | None = None, outdoors_plan: str | None = None, accessible: str | None = None, tags: list[Tag] | None = None, shifts: list[Shift] | None = None, need_status: str | None = None, created_at: str | None = None, background_check_required: str | None = None, updated_at: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

needObject – an opportunity an agency has posted.

id: int | None
domain_id: int | None
agency: AgencyMini | None
initiative: InitiativeMini | None
groups: list[GroupMini] | None
need_title: str | None
need_body: str | None
need_address: str | None
need_address2: str | None
need_city: str | None
need_state: str | None
need_postal: str | None
need_type: str | None
need_contact: str | None
need_response_notify: str | None
need_date: str | None
need_date_type: str | None
need_impact_area: str | None
need_volunteers_needed: str | None
need_public: str | None
need_allow_groups: str | None
need_hours: str | None
need_comments: str | None
need_latitude: str | None
need_longitude: str | None
need_date_close: str | None
family_friendly: str | None
outdoors: str | None
outdoors_plan: str | None
accessible: str | None
tags: list[Tag] | None
shifts: list[Shift] | None
need_status: str | None
created_at: str | None
background_check_required: str | None
updated_at: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

Qualifications

Models for the /qualifications endpoints.

Field names are copied verbatim from doc/api.yml; the API sends numeric ids as strings and pydantic coerces them.

class get_connected_client.models.qualifications.Qualification(*, id: int | None = None, domain_id: int | None = None, qualification_title: str | None = None, qualification_cat_id: int | None = None, qualification_question: str | None = None, qualification_type: str | None = None, qualification_options: list[str] | None = None, qualification_link_url: str | None = None, qualification_link_text: str | None = None, qualification_level: str | None = None, qualification_duration: str | None = None, qualification_approval: str | None = None, qualification_status: str | None = None, created_at: str | None = None, updated_at: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

qualificationObject – a credential a volunteer can hold or be asked for.

id: int | None
domain_id: int | None
qualification_title: str | None
qualification_cat_id: int | None
qualification_question: str | None
qualification_type: str | None
qualification_options: list[str] | None
qualification_level: str | None
qualification_duration: str | None
qualification_approval: str | None
qualification_status: str | None
created_at: str | None
updated_at: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.qualifications.QualificationUser(*, id: int | None = None, domain_id: int | None = None, user_fname: str | None = None, user_lname: str | None = None, user_email: str | None = None, status: str | None = None, expires: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

qualificationUsersObject – one user’s standing on a qualification.

id: int | None
domain_id: int | None
user_fname: str | None
user_lname: str | None
user_email: str | None
status: str | None
expires: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

Responses

Models for the /needs/{id}/responses endpoint.

Field names are copied verbatim from doc/api.yml; the API sends numeric ids as strings and pydantic coerces them.

class get_connected_client.models.responses.ResponseAnswer(*, type: str | None = None, key: str | None = None, area: str | None = None, question: str | None = None, answer: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

ResponseAnswerObject – one answer on a response’s question set.

type: str | None
key: str | None
area: str | None
question: str | None
answer: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.responses.Response(*, id: int | None = None, domain_id: int | None = None, agency: AgencyMini | None = None, shift: Shift | None = None, need: NeedMini | None = None, user: UserMini | None = None, initiative: InitiativeMini | None = None, team: TeamMini | None = None, response_phone: str | None = None, response_address: str | None = None, response_note: str | None = None, response_date_added: str | None = None, response_date_updated: str | None = None, response_source: str | None = None, response_status: str | None = None, response_comments: str | None = None, answers: list[ResponseAnswer] | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

responseObject – a volunteer’s response to a need.

id: int | None
domain_id: int | None
agency: AgencyMini | None
shift: Shift | None
need: NeedMini | None
user: UserMini | None
initiative: InitiativeMini | None
team: TeamMini | None
response_phone: str | None
response_address: str | None
response_note: str | None
response_date_added: str | None
response_date_updated: str | None
response_source: str | None
response_status: str | None
response_comments: str | None
answers: list[ResponseAnswer] | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

Teams

Models for the /teams endpoints.

Field names are copied verbatim from doc/api.yml; the API sends numeric ids as strings and pydantic coerces them.

class get_connected_client.models.teams.TeamMember(*, id: int | None = None, domain_id: int | None = None, user_fname: str | None = None, user_lname: str | None = None, user_email: str | None = None, leader: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

teamMembersObject – one member of a team.

id: int | None
domain_id: int | None
user_fname: str | None
user_lname: str | None
user_email: str | None
leader: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.teams.Team(*, id: int | None = None, domain_id: int | None = None, team_status: str | None = None, team_title: str | None = None, team_description: str | None = None, creator: UserMini | None = None, agency: AgencyMini | None = None, need: NeedMini | None = None, members: list[TeamMember] | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

teamObject – a group of volunteers responding together to one need.

id: int | None
domain_id: int | None
team_status: str | None
team_title: str | None
team_description: str | None
creator: UserMini | None
agency: AgencyMini | None
need: NeedMini | None
members: list[TeamMember] | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

Users

Models for the /users endpoints.

Field names are copied verbatim from doc/api.yml; the API sends numeric ids as strings and pydantic coerces them.

class get_connected_client.models.users.User(*, id: int | None = None, domain_id: int | None = None, domain_sitename: str | None = None, user_reference_id: str | None = None, user_fname: str | None = None, user_mname: str | None = None, user_lname: str | None = None, user_email: str | None = None, user_phone: str | None = None, user_phone_cell: str | None = None, user_username: str | None = None, user_address: str | None = None, user_address2: str | None = None, user_city: str | None = None, user_state: str | None = None, user_postal: str | None = None, user_county: str | None = None, user_country: str | None = None, user_age_range: str | None = None, user_disaster: str | None = None, user_birthday: str | None = None, user_company: str | None = None, user_company_title: str | None = None, user_department: str | None = None, user_ethnicity: str | None = None, user_gender: str | None = None, user_grad_semester: str | None = None, user_grad_year: str | None = None, user_notes: str | None = None, user_comments: str | None = None, user_status: str | None = None, created_at: str | None = None, updated_at: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

userObject – a site user (volunteer, manager or admin).

id: int | None
domain_id: int | None
domain_sitename: str | None
user_reference_id: str | None
user_fname: str | None
user_mname: str | None
user_lname: str | None
user_email: str | None
user_phone: str | None
user_phone_cell: str | None
user_username: str | None
user_address: str | None
user_address2: str | None
user_city: str | None
user_state: str | None
user_postal: str | None
user_county: str | None
user_country: str | None
user_age_range: str | None
user_disaster: str | None
user_birthday: str | None
user_company: str | None
user_company_title: str | None
user_department: str | None
user_ethnicity: str | None
user_gender: str | None
user_grad_semester: str | None
user_grad_year: str | None
user_notes: str | None
user_comments: str | None
user_status: str | None
created_at: str | None
updated_at: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.users.UserOneclick(*, link: str | None = None, expires: str | None = None, now: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

userOneclickObject – a short-lived passwordless login link.

expires: str | None
now: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.users.UserOptouts(*, id: int | None = None, email: str | None = None, optout_areas: list[str] | None = None, date_added: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

userOptoutsObject – the message areas a user has opted out of.

id: int | None
email: str | None
optout_areas: list[str] | None
date_added: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.users.UserQualification(*, id: int | None = None, domain_id: int | None = None, qualification_id: int | None = None, qualification_title: str | None = None, status: str | None = None, expires: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

userQualificationsObject – one qualification held by a user.

id: int | None
domain_id: int | None
qualification_id: int | None
qualification_title: str | None
status: str | None
expires: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.users.UserResponse(*, id: int | None = None, need_id: int | None = None, date_start: str | None = None, duration: str | None = None, status: str | None = None, created_at: str | None = None, updated_at: str | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

userResponseObject – a user’s signup for a need.

id: int | None
need_id: int | None
date_start: str | None
duration: str | None
status: str | None
created_at: str | None
updated_at: str | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].

class get_connected_client.models.users.RegistrationAnswer(*, type: str | None = None, key: str | None = None, area: str | None = None, question_id: int | None = None, question: str | None = None, answer: str | list[str] | None = None, **extra_data: Any)[source]

Bases: GalaxyModel

RegistrationResponseAnswerObject – one answer to a registration question.

answer is deliberately widened to str | list[str]: the read spec types it as a string, but the write shape (and multi-select questions on the wire) send a list of choices. Accepting both keeps a round trip – read, edit, write back – from failing validation.

type: str | None
key: str | None
area: str | None
question_id: int | None
question: str | None
answer: str | list[str] | None
model_config = {'extra': 'allow', 'populate_by_name': True, 'validate_by_alias': True, 'validate_by_name': True}

Configuration for the model, should be a dictionary conforming to [ConfigDict][pydantic.config.ConfigDict].