File size: 3,115 Bytes
50b6a4f
5ac4bad
50b6a4f
 
e5b68d3
50b6a4f
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
55ee703
50b6a4f
 
 
5ac4bad
 
 
50b6a4f
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
46fc9b1
5ac4bad
 
50b6a4f
c8e229a
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
# app.R
library(shiny)
library(httr2)

#The variable OPENAI_API_KEY uses the NVIDIA API_KEY
# Helper: resolve base URL (default to NVIDIA NIM OpenAI-compatible endpoint)
nim_base_url <- Sys.getenv("OPENAI_BASE_URL", unset = "https://integrate.api.nvidia.com/v1")

ui <- fluidPage(
  titlePanel("Chat com NVIDIA NIM via httr2 (Shiny)"),
  sidebarLayout(
    sidebarPanel(
      textInput("model", "Modelo (NIM)", value = "meta/llama-3.1-70b-instruct"),
      textAreaInput("system", "System prompt:", value = "You are a helpful assistant.", rows = 2),
      textAreaInput("pergunta", "Pergunta (user):", value = "Descreva o package leaflet no R.", rows = 4),
      sliderInput("temperature", "temperature:", min = 0, max = 1, value = 0.2, step = 0.1),
      numericInput("max_tokens", "max_tokens:", value = 400, min = 1, step = 50),
      actionButton("enviar", "Enviar", class = "btn-primary"),
      tags$hr(),
      helpText("Defina a variável de ambiente OPENAI_API_KEY nas configurações do Space.")
    ),
    mainPanel(
      h4("Resposta"),
      uiOutput("status"),
      verbatimTextOutput("resposta"),
      tags$hr(),
      #h5("Payload (debug)"),
      verbatimTextOutput("payload", placeholder = TRUE)
    )
  )
)

server <- function(input, output, session) {
  resposta <- reactiveVal("")
  status   <- reactiveVal("")
  payload  <- reactiveVal(NULL)

  observeEvent(input$enviar, {
    # checagens básicas
    if (Sys.getenv("OPENAI_API_KEY", unset = "") == "") {
      resposta("Erro: a variável OPENAI_API_KEY não está definida nas variáveis do Space.")
      return(invisible(NULL))
    }

    status("Enviando… aguarde")
    resposta("")

    body <- list(
      model = input$model,
      messages = list(
        list(role = "system", content = input$system),
        list(role = "user",   content = input$pergunta)
      ),
      temperature = input$temperature,
      max_tokens  = input$max_tokens
    )

    payload(body)

    req <- request(paste0(nim_base_url, "/chat/completions")) |>
      req_headers(
        Authorization = paste("Bearer", Sys.getenv("OPENAI_API_KEY")),
        `Content-Type` = "application/json"
      ) |>
      req_body_json(body)

    tryCatch({
      resp <- req_perform(req)
      if (resp_status(resp) >= 300) {
        status(paste("HTTP", resp_status(resp)))
      } else {
        status("OK")
      }
      out <- resp_body_json(resp)
      # compatível com OpenAI-style
      msg <- tryCatch(out$choices[[1]]$message$content, error = function(e) NULL)
      if (is.null(msg)) {
        # fallback: alguns provedores devolvem "text" direto
        msg <- tryCatch(out$choices[[1]]$text, error = function(e) "(sem conteúdo)")
      }
      resposta(msg)
    }, error = function(e) {
      status("Erro na requisição")
      resposta(paste("Erro:", e$message))
    })
  })

  output$resposta <- renderText(resposta())
  output$status   <- renderUI({
    s <- status()
    if (!nzchar(s)) return(NULL)
    div(style = "margin-bottom:8px;", strong("Status:"), span(s))
  })
  #output$payload  <- renderPrint(payload())
}

shinyApp(ui, server)