All files / src/core/bindings DurableObjectBinding.ts

37.5% Statements 6/16
0% Branches 0/4
14.28% Functions 1/7
40% Lines 6/15

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 11128x 28x                                         28x                                   28x   28x   28x                                                                                                                                    
import { Binding } from '@/core/bindings/Binding'
import { lazySettings } from '@/utils/lazySettings'
import { DurableObjectSettings } from '@/types/DurableObjectSettings'
import type { CloudflareEnv } from '@/types/CloudflareEnv'
 
/**
 * Accessor for the Durable Object namespace binding (`durable_objects` in
 * `wrangler.json`).
 *
 * @example
 * ```ts
 * const counters = new DurableObjectBinding() // binding name from the configuration layer
 * const stub = counters.stubByName(ctx.env, `room:${roomId}`)
 * const response = await stub.fetch('https://durable-object/increment')
 * ```
 *
 * @class
 *
 * @author Bayu Dwiyan Satria
 * @version 1.0.0
 * @since 1.0.0
 */
export class DurableObjectBinding<E extends CloudflareEnv = CloudflareEnv> extends Binding<DurableObjectNamespace, E> {
  /**
   * This accessor’s settings, resolved on first read.
   */
  private readonly settings: () => DurableObjectSettings
 
  /**
   * Default location hint applied when creating stubs.
   */
  private readonly locationHint?: DurableObjectLocationHint
 
  /**
   * Constructs a DurableObjectBinding instance.
   *
   * @param settings Resolved settings. Defaults to `resolve('durableObject')`, so callers
   *   normally construct this with no arguments at all.
   */
  constructor(settings?: DurableObjectSettings) {
    const settle = lazySettings<DurableObjectSettings>('durableObject', settings)
 
    super(() => settle().binding)
 
    this.settings = settle
  }
 
  /**
   * Returns the stub for the object derived from a name.
   *
   * The same name always maps to the same object, which is what makes this the
   * usual way to shard state by tenant, room, or user.
   *
   * @param env The Worker environment.
   * @param name The name to derive the object id from.
   * @returns The stub for that object.
   * @throws {@link MissingBindingError} When the Durable Object binding is absent.
   */
  public stubByName(env: E, name: string): DurableObjectStub {
    const namespace = this.resolve(env)
 
    return namespace.get(namespace.idFromName(name), this.stubOptions())
  }
 
  /**
   * Returns the stub for an existing object id.
   *
   * @param env The Worker environment.
   * @param id The object id, either as an id or its string form.
   * @returns The stub for that object.
   */
  public stubById(env: E, id: DurableObjectId | string): DurableObjectStub {
    const namespace = this.resolve(env)
    const objectId = typeof id === 'string' ? namespace.idFromString(id) : id
 
    return namespace.get(objectId, this.stubOptions())
  }
 
  /**
   * Creates a brand new object and returns its stub.
   *
   * @param env The Worker environment.
   * @returns The stub for the newly created object.
   */
  public stubForNewId(env: E): DurableObjectStub {
    const namespace = this.resolve(env)
 
    return namespace.get(namespace.newUniqueId(), this.stubOptions())
  }
 
  /**
   * Derives the object id for a name without creating a stub.
   *
   * @param env The Worker environment.
   * @param name The name to derive the object id from.
   * @returns The derived object id.
   */
  public idFromName(env: E, name: string): DurableObjectId {
    return this.resolve(env).idFromName(name)
  }
 
  /**
   * Builds the stub options carrying the configured location hint.
   *
   * @returns The stub options, or `undefined` when no hint is configured.
   */
  private stubOptions(): DurableObjectNamespaceGetDurableObjectOptions | undefined {
    return this.settings().locationHint ? { locationHint: this.settings().locationHint } : undefined
  }
}