# Exponer en la LAN

Publica el agente en la dirección LAN del router con install --expose, las dos reglas de cortafuegos etiquetadas que añade, quién llega al agente a través de ellas, el token que exigen y cómo se quitan.

Source: https://docs.jmrp.io/mikroscope/es/security/expose/

`--expose` publica el agente en la dirección LAN del router, para un cliente que no llega a la /30 de
la veth: un job de Prometheus, un navegador, `curl`. Añade dos reglas de cortafuegos etiquetadas y
hace obligatorio un token.

```sh
mikroscope install --expose --lan-address 192.168.88.1
```

Guarda el token en `MIKROSCOPE_TOKEN`, que lo mantiene fuera de la línea de órdenes.

**Lo que añade `install --expose`**

- dos reglas de cortafuegos, etiquetadas
- el token pasa a ser obligatorio
- `uninstall` y `status` encuentran las dos reglas por el manifiesto y la etiqueta, con `--expose` o sin él

Cada objeto lleva el comentario `mikroscope:<name> (managed by mikroscope)`

`mikroscope plan` imprime cada orden antes de escribir nada.

## Alcance por defecto

El agente escucha en la dirección del contenedor, la `.2` de `--subnet` (`172.30.10.2` por
defecto), en `--port` (`9123`). Sin `--expose` solo se llega a él desde las máquinas que el router
encamina hacia esa /30 de la veth, gracias a las dos pertenencias a listas que añade toda instalación
([Acceso por red](https://docs.jmrp.io/mikroscope/es/install/reaching-the-agent/)).

## Reglas del cortafuegos

`install --expose` añade, después de las pertenencias a listas y antes del contenedor, un dst-nat
desde la dirección LAN del router en el puerto del agente hacia la veth:

```routeros
/ip/firewall/nat/add chain=dstnat dst-address=<router LAN IP> protocol=tcp dst-port=9123 action=dst-nat to-addresses=172.30.10.2 to-ports=9123 comment="mikroscope:mikroscope (managed by mikroscope)"
```

y un accept en forward para ese flujo, colocado antes de la primera regla `chain=forward
action=drop`, o añadido al final cuando la cadena forward no tiene ningún drop:

```routeros
/ip/firewall/filter/add chain=forward dst-address=172.30.10.2 protocol=tcp dst-port=9123 connection-nat-state=dstnat action=accept comment="mikroscope:mikroscope (managed by mikroscope)" place-before=<first forward drop>
```

- Las direcciones y el puerto son los valores por defecto. `<first forward drop>` representa la
  búsqueda que hace la orden real en el router antes de añadir la regla. `plan` imprime las dos
  órdenes exactamente como se ejecutan, con tus valores.
- Las dos llevan la etiqueta. El par permite que la LAN llegue al agente a través de la dirección del
  propio router ([verificado](https://docs.jmrp.io/mikroscope/es/about/status/#verified-expose-rules)).
- `--lan-address` tiene que ser una dirección IPv4; `install` rechaza `--expose` sin ella
  (`--expose needs the router's IPv4 LAN address`). `doctor` comprueba que una interfaz del router
  tenga esa dirección y que no esté en el enlace de subida.
- Una regla existente con la misma cadena, dirección de destino, puerto y protocolo que no lleve la
  etiqueta detiene `install`, como cualquier objeto ajeno ([Salvaguardas del
  instalador](https://docs.jmrp.io/mikroscope/es/security/installer/)).

## Máquinas que llegan

Cualquier máquina de la LAN llega al agente en `<router LAN IP>:9123`. Ninguna de las dos reglas
restringe el origen: el dst-nat no tiene `in-interface` ni `src-address`, y el accept solo compara el
destino, el puerto y `connection-nat-state=dstnat`. Qué máquinas pasan lo decide qué máquinas pueden
enviar un paquete a la dirección LAN del router, y lo que hagan tus otras reglas antes que estas. Si
algo de fuera de la LAN llega a esa dirección depende del resto de tu cortafuegos, que mikroscope ni
lee ni cambia ([sin probar](https://docs.jmrp.io/mikroscope/es/about/status/#not-tested)).

## Token

Como al agente ya no se llega solo a través de la veth, `install` y `upgrade` rechazan `--expose`
sin token (`--expose makes the agent reachable from the LAN: a token is mandatory`).

Con un token puesto, todos los endpoints que sirve el agente salvo `/healthz` devuelven
`401 token required`, con `WWW-Authenticate: Bearer`, a menos que la petición lleve
`Authorization: Bearer <token>`: `/capabilities`, `/sampler`, `/snapshot`, `/stream`, `/captures`,
`/captures/{id}` (incluido `DELETE`) y `POST /capture`. Una ruta que el agente no sirve recibe `404`,
y un método equivocado `405`, haya token o no. El agente quita un prefijo `"Bearer "` opcional antes
de comparar, así que también se acepta una cabecera que lleve el token a secas.

`/healthz` sigue abierto. Devuelve la versión del agente, la cadencia, los números de secuencia, el
tiempo en marcha, la cuenta de retrasos, el hash de capacidades, sus relojes de pared y monótono, y
el modelo del device-tree de la placa. El modelo está ahí a propósito: es lo que se le pide a un
operador que envíe cuando su placa aún no tiene mapa de puertos del kernel a RouterOS.

Lo que el token es, y lo que no:

- Puede contener letras, dígitos, `_`, `.` y `-`, hasta 128 caracteres; cualquier otra cosa se
  rechaza antes de la primera orden.
- Se guarda en la envlist como `TOKEN`. Un usuario `read,api` puede listar la propiedad `envlist` de
  cualquier contenedor ([verificado](https://docs.jmrp.io/mikroscope/es/about/status/#verified-read-user-envlist)); no se comprobó si
  ese usuario lee los valores de las entradas, y el diseño supone que puede. Tómalo como protección
  de las rutas HTTP del agente frente a la LAN, no frente a los propios usuarios `read` del router.
- `doctor`, `status` y `upgrade` cuentan las entradas `TOKEN` y nunca leen su valor; el manifiesto
  de la instalación dice solo `token=yes` o `token=no`.
- Un token puesto sin `--expose` se escribe igualmente y se exige igualmente.
- El agente lo compara como una cadena normal, sobre HTTP sin cifrar: el dst-nat no lleva TLS, así
  que la cabecera cruza la LAN sin cifrar.

## Clientes de la dirección

Las reglas sirven a un cliente que se dirige a `<router LAN IP>:<port>`: un job de Prometheus, un
navegador, un `curl` con la cabecera. Las órdenes de mikroscope no usan esa dirección:

- `record` y `forward` construyen la URL del agente a partir de `--subnet` y `--port`, así que
  siempre marcan la dirección del contenedor. Ninguna opción las apunta a la dirección LAN.
- `install`, `upgrade` y `status` también sondean `/healthz` en la dirección del contenedor, y
  `doctor` lee allí `/healthz` y después el anillo del agente, presentando el token si se le da.
- El transporte relay no puede llevar el token: `/tool fetch` en el router no envía cabecera
  `Authorization`. Contra un agente con token, el `/healthz` del relay responde y toda petición de
  muestras se rechaza. Un token necesita el transporte directo, o un despliegue sin token.

## Actualizar

`upgrade` conserva las dos reglas. Lee en el router que la instalación está expuesta, quita el paso
del contenedor (el contenedor, la envlist `<name>-env` y la imagen) y lo vuelve a crear, con la
envlist escrita a partir de las opciones que recibe `upgrade`.

- Rechaza una instalación cuya envlist tiene un `TOKEN` cuando no recibe token:
  `the install named mikroscope asks for a token and upgrade would write its envlist without one: pass --token (or MIKROSCOPE_TOKEN)`.
- Una opción de ajuste que falte vuelve a su valor por defecto. Pasa los `--rate`, `--buffer`,
  `--mem-limit-mb`, `--capture-mb`, `--triggers`, `--floor-hz`, `--memory-max`, `--privileged`,
  `--restart-max-count` y `--restart-interval` con los que instalaste.

> **Un agente expuesto sin token**
>
> Una instalación con el mismo `--name` que tiene un dst-nat etiquetado y ninguna entrada `TOKEN`
> está publicada en la LAN sin token. `doctor` avisa de ello, contando las entradas sin leer nunca un
> valor: `WARN the installed agent published on the LAN asks for a token`. Su solución es
> `mikroscope upgrade --name <name> --token <secret>`, o `mikroscope uninstall --name <name> --yes`,
> que quita el agente y las dos reglas.

## Quitar las reglas

`uninstall` quita las dos reglas con el resto de la instalación. Lee la forma de la instalación en el
router, así que no necesita `--expose` ni `--lan-address`, ni ningún token:

```sh
mikroscope uninstall        # lists what it would remove, the two rules included
mikroscope uninstall --yes  # removes it
```

- Cada regla se selecciona por la etiqueta junto con la cadena, la dirección de destino, el puerto y
  el protocolo. Cualquier otro objeto que lleve la etiqueta de la instalación en `/ip/firewall/nat`
  o `/ip/firewall/filter` se quita por la etiqueta.
- Después cuenta lo que queda, por paso y por menú, y falla nombrando lo que siga ahí.
- Esos selectores `find` ponen entre comillas todo valor no numérico salvo los enumerados `chain` y
  `action`. Sin comillas, una dirección o un puerto se interpretan como valores tipados y no
  encuentran nada ([verificado](https://docs.jmrp.io/mikroscope/es/about/status/#verified-find-quoting)), y una palabra suelta como
  `tcp` se lee como el nombre de una variable, cuyo valor sin definir es vacío.

## Véase también

- [Acceso por red](https://docs.jmrp.io/mikroscope/es/install/reaching-the-agent/): directo, relay y `--expose`
  comparados.
- [Modelo de seguridad](https://docs.jmrp.io/mikroscope/es/security/): dónde está el token entre las demás credenciales.
- [Salvaguardas del instalador](https://docs.jmrp.io/mikroscope/es/security/installer/): las comprobaciones de propiedad
  por las que pasa cada regla.
- [Endpoints HTTP](https://docs.jmrp.io/mikroscope/es/reference/http/): cada ruta que protege el token.
