Skip to main content

ssh_cli/platform/
mod.rs

1//! Abstrações condicionais por sistema operacional.
2//!
3//! A inicialização de plataforma ([`inicializar_plataforma`]) é a PRIMEIRA operação
4//! executada no `main()`. Ela configura:
5//!
6//! - **Windows**: codepage UTF-8 (65001) via `SetConsoleOutputCP` e `SetConsoleCP`
7//! - **Linux**: detecção de sandbox (Flatpak/Snap) e caminhos XDG
8//! - **macOS**: resolução de caminhos de config em `~/Library/Application Support`
9
10use anyhow::Result;
11
12#[cfg(target_os = "linux")]
13mod linux;
14#[cfg(target_os = "macos")]
15mod macos;
16#[cfg(target_os = "windows")]
17mod windows;
18
19/// Inicializa a plataforma antes de qualquer I/O.
20///
21/// DEVE ser chamado como a primeira operação em `main()`.
22pub fn inicializar_plataforma() -> Result<()> {
23    #[cfg(target_os = "windows")]
24    {
25        windows::configurar_codepage_utf8()?;
26    }
27
28    #[cfg(target_os = "linux")]
29    {
30        linux::detectar_sandbox();
31    }
32
33    #[cfg(target_os = "macos")]
34    {
35        macos::inicializar();
36    }
37
38    Ok(())
39}
40
41/// Normaliza uma linha de stdin removendo `\r` final (CRLF → LF).
42///
43/// Necessário no Windows onde pipes podem emitir `\r\n`.
44#[must_use]
45pub fn normalizar_linha_stdin(linha: &str) -> &str {
46    // Remove qualquer combinação de CR/LF do final.
47    linha.trim_end_matches(['\r', '\n'])
48}
49
50/// Retorna `true` se stdout está conectado a um terminal (TTY).
51#[must_use]
52pub fn e_tty() -> bool {
53    std::io::IsTerminal::is_terminal(&std::io::stdout())
54}
55
56#[cfg(test)]
57mod testes {
58    use super::*;
59
60    #[test]
61    fn normalizar_remove_cr_final() {
62        assert_eq!(normalizar_linha_stdin("teste\r"), "teste");
63        assert_eq!(normalizar_linha_stdin("teste\r\n"), "teste");
64        assert_eq!(normalizar_linha_stdin("teste\n"), "teste");
65        assert_eq!(normalizar_linha_stdin("teste"), "teste");
66    }
67
68    #[test]
69    fn normalizar_string_vazia() {
70        assert_eq!(normalizar_linha_stdin(""), "");
71    }
72
73    #[test]
74    fn normalizar_apenas_newlines() {
75        assert_eq!(normalizar_linha_stdin("\n\n\n"), "");
76    }
77
78    #[test]
79    fn normalizar_mistos_crlf_lf() {
80        assert_eq!(
81            normalizar_linha_stdin("linha1\r\nlinha2\r\nlinha3"),
82            "linha1\r\nlinha2\r\nlinha3"
83        );
84    }
85
86    #[test]
87    fn normalizar_com_espacos() {
88        assert_eq!(
89            normalizar_linha_stdin("texto com espacos  \r\n"),
90            "texto com espacos  "
91        );
92    }
93
94    #[test]
95    fn e_tty_retorna_bool() {
96        let _ = e_tty();
97    }
98}