1import * as Effect from "effect/Effect";
2import * as Binding from "../Binding.ts";
3import type { Zone } from "./Zone.ts";
4import { type ReadDnsClient } from "./ReadDns.ts";
5import { type WriteDnsClient } from "./WriteDns.ts";
6
7/**
8 * Binding that lets runtime code perform the full Hetzner Cloud DNS RRSet
9 * surface (read + write).
10 *
11 * Authenticates with the ambient `HCLOUD_TOKEN`. The zone is fixed by
12 * `ReadWriteDns(zone)` so calls take no zone id. Provide
13 * {@link ReadWriteDnsHttp} on the Action / Function Effect.
14 *
15 *
16 * ### Managing RRSets at runtime
17 * **Example:** Full CRUD from an Action
18 * Bind the client in the Action's Init phase and provide
19 * {@link ReadWriteDnsHttp}.
20 * ```typescript
21 * import * as Alchemy from "alchemy";
22 * import * as Hetzner from "alchemy/Hetzner";
23 * import * as Effect from "effect/Effect";
24 *
25 * const Seed = Alchemy.Action(
26 * "Seed",
27 * Effect.gen(function* () {
28 * const dns = yield* Hetzner.ReadWriteDns(zone);
29 * return Effect.fn(function* () {
30 * const created = yield* dns.createRecordSet({
31 * name: "app",
32 * type: "A",
33 * records: [{ value: "192.0.2.1" }],
34 * ttl: 300,
35 * });
36 * yield* Hetzner.waitForZoneAction(created.action);
37 * const rrset = yield* dns.getRecordSet("app", "A");
38 * yield* dns.deleteRecordSet("app", "A");
39 * return rrset.rrset.id;
40 * });
41 * }).pipe(Effect.provide(Hetzner.ReadWriteDnsHttp)),
42 * );
43 * ```
44 *
45 * @binding
46 * @product DNS
47 */
48export interface ReadWriteDns extends Binding.Service<
49 ReadWriteDns,
50 "Hetzner.DNS.ReadWriteDns",
51 (zone: Zone) => Effect.Effect<ReadWriteDnsClient>
52> {}
53
54export const ReadWriteDns = Binding.Service<ReadWriteDns>(
55 "Hetzner.DNS.ReadWriteDns",
56);
57
58/** Combined read + write DNS RRSet operations. */
59export interface ReadWriteDnsClient extends ReadDnsClient, WriteDnsClient {}