# Daily logs

Every day a crew works a visit has a **daily log**: its sign-off status and notes, plus the **daily reports** the crew filed from the TruTec crew app (weather, work performed, delays, safety, materials, equipment and quantity completed). Time punches for the day are [time entries](timesheets.md).

When the workspace uses daily log sign-off, a day moves `draft` → `submitted` (the foreman submits) → `office_approved` → `payroll_approved` (only when payroll gives a second sign-off). Office approval approves the day's time for payroll.

Writes act as the person who created the API key; they must be an office user (not a crew login). A day payroll has approved can't be changed until a payroll approver sends it back (`409`).

## The daily log object

| Field | Type | Description |
|---|---|---|
| `id` | integer | |
| `work_order_id`, `job_id` | integer | The visit and job. |
| `date` | string | The work day. |
| `status` | string | `draft`, `submitted`, `office_approved` or `payroll_approved`. |
| `notes` | string or null | Day notes from the foreman or office. |
| `submitted_at`, `submitted_by` | | When and who submitted. |
| `office_approved_at`, `office_approved_by`, `payroll_approved_at`, `payroll_approved_by` | | Sign-offs. |
| `returned_at`, `return_note` | | The last send-back and why. |
| `daily_reports` | array | The crew's reports for that visit and day (single-log reads only). |
| `created_at`, `updated_at` | string | UTC. |

## Daily logs

### List daily logs

`GET /v1/daily-logs`

**Permission:** Read jobs

Newest day first. With `updated_after`, sorted by `updated_at`, oldest first.

| Name | Type | Required | Description |
|---|---|---|---|
| `start_date`, `end_date` | string | No | Work days. |
| `job_id`, `work_order_id` | integer | No | |
| `status` | string | No | One of the statuses above. |
| `updated_after` | string | No | ISO 8601. |
| `limit`, `offset` | integer | No | Default 50, maximum 200. |

```bash
curl "https://trutec.ai/api/v1/daily-logs?status=submitted" \
  -H "X-API-Key: sk_your_api_key_here"
```

```json
{
  "data": [
    {
      "id": 9120,
      "work_order_id": 4120,
      "job_id": 70412,
      "date": "2026-11-03",
      "status": "submitted",
      "notes": "Rain delay until 10am",
      "submitted_at": "2026-11-03T23:41:09Z",
      "submitted_by": { "id": 344, "name": "Crew Lead" },
      "office_approved_at": null,
      "office_approved_by": null,
      "payroll_approved_at": null,
      "payroll_approved_by": null,
      "returned_at": null,
      "return_note": null,
      "created_at": "2026-11-03T13:02:44Z",
      "updated_at": "2026-11-03T23:41:09Z"
    }
  ],
  "pagination": { "total": 1, "limit": 50, "offset": 0 }
}
```

### Get a daily log

`GET /v1/daily-logs/{id}`

**Permission:** Read jobs

The log with the day's `daily_reports`.

### Add office notes to a day

`POST /v1/daily-logs`

**Permission:** Write jobs

Saves the office's notes on a visit's day, creating that day's log if it has none yet. Returns `200` with the log.

| Name | Type | Required | Description |
|---|---|---|---|
| `work_order_id` | integer | Yes | |
| `date` | string | Yes | The work day. |
| `notes` | string | Yes | Replaces the day's notes. |

```bash
curl -X POST "https://trutec.ai/api/v1/daily-logs" \
  -H "X-API-Key: sk_your_api_key_here" \
  -H "Content-Type: application/json" \
  -d '{ "work_order_id": 4120, "date": "2026-11-03", "notes": "Rain delay until 10am" }'
```

### Approve a day, or send it back

`POST /v1/daily-logs/{id}/approve`

`POST /v1/daily-logs/{id}/send-back` with `{"note": "Missing the second truck"}`

**Permission:** Write jobs

Approve signs off a submitted day as the office (or as payroll, for an office-approved day when the key's creator is a payroll approver). Send back returns the day to the foreman as a draft with your note. When the workspace does not use sign-off, both return `409`.

## Crew daily reports

### List daily reports

`GET /v1/daily-reports`

**Permission:** Read jobs

Takes `job_id`, `work_order_id`, `start_date`, `end_date`, `limit` and `offset`. Newest first.

```json
{
  "data": [
    {
      "id": 66120,
      "job_id": 70412,
      "work_order_id": 4120,
      "estimate_service_id": 55120,
      "date": "2026-11-03",
      "submitted_by": { "id": 344, "name": "Crew Lead" },
      "weather": "Overcast, 58°F",
      "work_performed": "Cleaned and crack-filled the east lot; first coat down.",
      "delay_notes": "Rain until 10am",
      "safety_notes": null,
      "material_notes": "Used 600 gal sealer",
      "equipment_notes": null,
      "completed_quantity": 21000.0,
      "completed_unit": "SF",
      "answers": { "Was the site clear when you arrived?": "Yes" },
      "photo_count": 6,
      "created_at": "2026-11-03T23:40:51Z"
    }
  ],
  "pagination": { "total": 1, "limit": 50, "offset": 0 }
}
```

`answers` holds the workspace's own daily-report questions. Photos are counted here; read them with the job's photos endpoints.

### Get a daily report

`GET /v1/daily-reports/{id}`

**Permission:** Read jobs

Daily reports are filed from the crew app; the API reads them and can email them.

### Email a daily report

`POST /v1/daily-reports/{id}/send`

**Permission:** Write jobs

!!! warning
    This emails someone outside your workspace. The report goes to the address you give, from the connected mailbox of the person who created the API key, and cannot be unsent.

Sends the report's summary (weather, work performed, production, delays, safety, materials and equipment) to one address, such as the customer or the general contractor, like **Email report** in TruTec.

| Field | Type | Required | Description |
|---|---|---|---|
| `to_email` | string | Yes | One email address. |

```bash
curl -X POST "https://trutec.ai/api/v1/daily-reports/66120/send" \
  -H "X-API-Key: sk_your_api_key_here" \
  -H "Content-Type: application/json" \
  -d '{ "to_email": "super@generalcontractor.example" }'
```

Returns the report as `data` and `emailed_to`. When the email can't be sent (for example the key creator has no connected mailbox), the response is `502` and nothing is recorded as sent.
