# Expo

> Miniapps dentro del Host nativo y aplicaciones de Expo que hablan con Andco.


Expo aparece en dos papeles distintos y conviene no confundirlos.

- **Escribes una Miniapp** que corre dentro del Host de Andco. Tu código es web y usa el constructor de navegador; el puente nativo se detecta solo.
- **Escribes un Host** que embebe Miniapps. Ahí usas `@andco/sdk-react-native-webview`.

## Escribir una Miniapp

Una Miniapp es una aplicación web. Dentro del Host tiene un puente nativo; en una pestaña del navegador no. **No escribes dos caminos**: el mismo código corre en ambos.

```bash
npm install @andco/sdk @andco/sdk-react
```

```tsx title="src/main.tsx"
import { AndcoProvider } from "@andco/sdk-react";

const clientOptions = {
  clientId: import.meta.env.VITE_ANDCO_CLIENT_ID,
  redirectTo: new URL("/", window.location.origin).href,
  initialScopes: ["openid", "email", "profile"],
} as const;

<AndcoProvider clientOptions={clientOptions}>
  <App />
</AndcoProvider>;
```

Eso es todo. El presentador del navegador detecta el Host y enruta la autorización por el puente en vez de abrir una ventana; fuera del Host abre la ventana como siempre. Por eso no hay un constructor «para móvil» ni un paquete distinto.

### Saber dónde estás corriendo

A veces sí importa: una Miniapp puede ofrecer algo que solo tiene sentido dentro del Host.

```ts
import { isAndcoNativeHost } from "@andco/sdk/browser";

if (isAndcoNativeHost()) {
  showHostShortcut();
}
```

Úsalo para decidir qué muestras, nunca para decidir cómo autenticas: eso ya está resuelto.

### Presentaciones que el Host no soporta

Un Host nativo no siempre puede presentar una ventana emergente sin abandonar la Miniapp. Cuando no puede, el SDK falla con `presentation_unsupported` en vez de hacer algo a medias.

```ts
const { error } = await andco.auth.signIn();
if (error?.code === "presentation_unsupported") {
  await andco.auth.signIn({ presentation: "redirect" });
}
```

## Escribir un Host

```bash
npx expo install @andco/sdk-react-native-webview react-native-webview
```

```tsx title="app/miniapp.tsx"
import { AndCoWebView } from "@andco/sdk-react-native-webview";

export default function Screen({ miniapp, accessToken }: Props) {
  return (
    <AndCoWebView
      miniapp={miniapp}
      accessToken={accessToken}
      bankOrigin="https://bank.andco.cl"
      authorizationOrigins={["https://auth.andco.cl"]}
      onError={(error) => console.error(error.code)}
      style={{ flex: 1 }}
    />
  );
}
```

`AndCoWebView` embebe la Miniapp y reemplaza su ventana emergente por consentimiento nativo de primera parte. La Miniapp no cambia una línea.

### Consentimiento nativo propio

Si quieres presentar el consentimiento con los componentes de tu plataforma —una `BottomSheet` de Expo, por ejemplo— entrega tu propio presentador:

```tsx
<AndCoWebView
  miniapp={miniapp}
  accessToken={accessToken}
  bankOrigin="https://bank.andco.cl"
  authorizationOrigins={["https://auth.andco.cl"]}
  authorizationPresenter={MyPresenter}
/>
```

Tu presentador recibe el estado de la presentación y las funciones para aprobar o rechazar. `AndCoConsentContent` dibuja el contenido oficial del consentimiento, así que puedes quedarte solo con el contenedor.

### Qué orígenes confías

`authorizationOrigins` es la lista de orígenes que pueden participar en la autorización. No es decorativa: es lo que impide que una página cargada dentro del WebView se haga pasar por el servidor de autorización. Ponla explícita y corta.
