---
title: "Add to existing project"
description: "Take a Go service that already posts webhooks by hand and move one ad-hoc HTTP call onto a generated, typed Repost sender in about 15 minutes."
---


<RepostHighlight />

You already have a service that posts webhooks to your customers with `net/http` and a hand-built JSON body. This guide replaces one of those calls with a generated, typed sender: no rewrite, no big bang. Set aside about 15 minutes.

You start from something like this, scattered wherever an event happens:

```go
// The ad-hoc send you have today.
body, _ := json.Marshal(map[string]any{
    "type": "order.created",
    "data": map[string]any{"id": order.ID, "currency": order.Currency},
})
http.Post(customer.WebhookURL, "application/json", bytes.NewReader(body))
```

Go 1.25 or later is required.

<Steps>
  <Step title="Install the runtime">
    Add the `repost` runtime module to your existing project. It carries no third-party dependencies.

    ```bash
    go get github.com/repost-sh/repost-go
    ```

    The module is imported under the alias `repost` in the examples that follow.
  </Step>

  <Step title="Initialize a schema in your repo">
    From the repository root:

    ```bash
    repost schema init --language go --output ./internal/repostclient
    ```

    This scaffolds a `repost/` directory with a starter schema and a `.env` file for your key. The generated package is written into your repo and committed, like `protoc` or `sqlc` output.
  </Step>

  <Step title="Model the event you already send">
    Edit `repost/schema.repost` so the model and event match the payload your ad-hoc call sends today. For the `order.created` example above:

    ```repost repost/schema.repost
    generator sdk {
      language = "go"
      output   = "../internal/repostclient"
    }

    model Order {
      id       String
      currency String
    }

    type Order {
      created
    }

    event OrderCreated {
      type      @type(Order.created)
      data      Order
      timestamp DateTime
    }
    ```

    Add one field per key you send today. [Schema](/docs/send/schema) covers enums, nested models, and more.
  </Step>

  <Step title="Record the schema and generate">
    ```bash
    repost schema migrate dev --name init
    ```

    This records your schema as a migration and writes the client package into `internal/repostclient`. Commit it. [Code generation](/docs/send/go/generation) covers every file it emits and how regeneration works.
  </Step>

  <Step title="Connect an environment">
    Create an environment in the [dashboard](https://app.repost.sh), copy its publish API key into `.env`, then deploy your schema:

    ```bash
    repost auth login
    repost schema migrate deploy
    ```
  </Step>
</Steps>

## Replace the ad-hoc call

Swap the raw `http.Post` for the generated sender. Repost fans the event out to the customer's registered endpoints, so you no longer track `WebhookURL` yourself:

```go
client, err := repostclient.NewClient(repost.ClientOptions{})
if err != nil {
    log.Fatal(err)
}

result, err := client.Webhooks.Order.Created(context.Background(), repostclient.OrderCreatedInput{
    CustomerID:     "acme",
    Data:           repostclient.Order{ID: "order-1001", Currency: "EUR"},
    IdempotencyKey: "order-1001:created",
})
if err != nil {
    log.Fatal(err)
}

fmt.Printf("sent %s as %s\n", result.ID, result.Type)
```

`NewClient` only checks that the generated package and runtime are compatible; everything else is lazy. The API key resolves at send time from `ClientOptions.APIKey`, then `REPOST_SEND_API_KEY`, then `REPOST_TOKEN`. Leaving `IdempotencyKey` empty lets the runtime mint one per send.

## Verify delivery

Trigger the code path that fires the event, then open the [dashboard](https://app.repost.sh). The send appears in the event stream with its `msg_...` id and per-endpoint delivery status. Once you trust it, delete the old `http.Post` call and repeat for the next event type.

## Continue

<Columns cols={3} className="gap-y-4">
  <Card title="Code generation" icon="cog" href="/docs/send/go/generation" cta="Generation" arrow="true">
    What the generator emits, and how the generated types work.
  </Card>

  <Card title="Model your events" icon="table" href="/docs/send/schema" cta="Schema" arrow="true">
    Enums, nested models, and the full schema language.
  </Card>

  <Card title="Reliability" icon="shield-check" href="/docs/send/go/reliability" cta="Errors" arrow="true">
    Retries, idempotency, and the error surface.
  </Card>
</Columns>
