# `MishkaCmsMigration.Resources.Changes.CheckConnection`
[🔗](https://github.com/mishka-group/mishka_cms_migration/blob/v0.0.1/lib/mishka_cms_migration/resources/__changes/check_connection.ex#L5)

Connects to a new run's source before the run is saved
(`MishkaCmsMigration.Source.connect/4`, with the run's `connection` and its sealed secret
opened), so a run is only kept for a source it can reach; a refusal is also told on telemetry.
What the source says of itself
(`c:MishkaCmsMigration.Source.extra/1`) becomes the run's `extra`.

A run that names no `source_host` takes the host its source reads from the connection
(`c:MishkaCmsMigration.Source.host/1`), so an admin types the address once. The action lists
`source_host` in `allow_nil_input`, so a connection with no host is refused once, on the
connection, rather than again as a missing host.

A refusal is an error on the run's `connection`, in words for the reasons
`MishkaCmsMigration.Source` names and as the reason itself for any other; a connection the
source reads no host from is refused as `:invalid_address`. For a source that reads a file
(`c:MishkaCmsMigration.Source.file?/0`) it is an error on the run's `file`, the form's upload,
instead: `:no_file` when the run was handed none and `:unreadable_file` when the source reads no
host from it, both put in words as well. A run of a source that is not installed is left to
`MishkaCmsMigration.Resources.Validations.SourceInstalled`.

    create :create do
      allow_nil_input [:source_host]
      change MishkaCmsMigration.Resources.Changes.CheckConnection
      validate present(:source_host), only_when_valid?: true
      change &MishkaCmsMigration.MigrationRun.seal_secret/2
    end

The source is handed the connection as the run keeps it, as JSON with string keys, which is how
a job reads it back; guarded_struct has turned the keys it knows into atoms by then.

It connects in a `before_transaction` hook: once, when the action runs, outside its
transaction, and never while a form only validates what is typed. The hook opens the secret
`seal_secret/2` sealed, so it needs that change in the same action, and for a source that reads
a file it needs `MishkaCmsMigration.Resources.Changes.SourceFile` before it, which keeps the file
in its own hook first.

# `message`

```elixir
@spec message(module(), term()) :: String.t()
```

What a refusal of `source` for `reason` says to the admin, translated: the words of a reason
`MishkaCmsMigration.Source` names, such as "Nothing answered at this address.", else
"Could not connect to …" with the reason. The New import window's Next says it as the save does
(`MishkaCmsMigrationWeb.Live.Admin.Dashboard.ImportSteps`).

---

*Consult [api-reference.md](api-reference.md) for complete listing*
