Bootsnap::CompileCache::PermissionError

Ciao a tutti. Ho appena installato Discourse su Docker.
Il problema è che, dopo il rebuild del container, questo si avvia e riesco ad accedere alla pagina dell’applicazione. Tuttavia, ricevo una risposta 502. Nei log o quando provo ad accedere, ad esempio, tramite rails c (all’interno del container), l’unico errore che vedo è questo:
`permission_error’: bootsnap non ha i permessi per scrivere le voci della cache in ‘tmp/cache/bootsnap/compile-cache’ (o, meno probabilmente, non ha i permessi per leggere ‘/usr/local/lib/ruby/2.7.0/set.rb’) (Bootsnap::CompileCache::PermissionError)

Per risolvere il problema devo eseguire chown -R discourse:discourse /var/www/discourse/tmp (più precisamente, la directory è /var/www/discourse/tmp/cache/bootsnap) all’interno del container. Subito dopo, l’app funziona correttamente anche senza riavvio. È piuttosto fastidioso doverlo fare manualmente dopo ogni rebuild.

Stavo pensando di risolvere il problema utilizzando la sezione dei comandi personalizzati in app.yml con il comando chown -R discourse:discourse /var/www/discourse/tmp menzionato sopra, ma purtroppo non funziona. I comandi sembrano essere eseguiti (ho provato con mkdir solo per verificare), ma i permessi dei file non vengono modificati.

Qual potrebbe essere il problema e come si può risolvere? Forse esiste un modo corretto per modificare i permessi dei file?

Strano. Hai seguito l’Installazione standard ufficiale di Discourse?

Certo. Non sono stati compiuti ulteriori passaggi.

Puoi incollare il tuo file container.yml (senza password)?

Certo. Ecco a te:

## questo è il template del contenitore Docker Discourse all-in-one e autonomo
##
## Dopo aver apportato modifiche a questo file, DEVI ricostruire
## /var/discourse/launcher rebuild app
##
## FAI MOLTO MOLTO ATTENZIONE DURANTE LA MODIFICA!
## I FILE YAML SONO SUPER SUPER SENSIBILI A ERRORI NEGLI SPAZI O NELL'ALLINEAMENTO!
## visita http://www.yamllint.com/ per convalidare questo file quando necessario

templates:
  - "templates/postgres.template.yml"
  - "templates/redis.template.yml"
  - "templates/web.template.yml"
  - "templates/web.ratelimited.template.yml"
## Rimuovi il commento da queste due righe se desideri aggiungere Lets Encrypt (https)
  - "templates/web.ssl.template.yml"
  #- "templates/web.letsencrypt.ssl.template.yml"

## quali porte TCP/IP deve esporre questo contenitore?
## Se desideri che Discourse condivida una porta con un altro server web come Apache o nginx,
## consulta https://meta.discourse.org/t/17247 per i dettagli
expose:
  - "80:80"   # http
  - "443:443" # https

params:
  db_default_text_search_config: "pg_catalog.english"

  ## Imposta db_shared_buffers a un massimo del 25% della memoria totale.
  ## verrà impostato automaticamente da bootstrap in base alla RAM rilevata, oppure puoi sovrascrivere
  #db_shared_buffers: "256MB"

  ## può migliorare le prestazioni di ordinamento, ma aumenta l'utilizzo della memoria per connessione
  #db_work_mem: "40MB"

  ## Quale revisione di Git deve utilizzare questo contenitore? (predefinito: tests-passed)
  #version: tests-passed

env:
  LC_ALL: en_US.UTF-8
  LANG: en_US.UTF-8
  LANGUAGE: en_US.UTF-8
  # DISCOURSE_DEFAULT_LOCALE: en

  ## Quanti richieste web simultanee sono supportate? Dipende dalla memoria e dai core della CPU.
  ## verrà impostato automaticamente da bootstrap in base alle CPU rilevate, oppure puoi sovrascrivere
  #UNICORN_WORKERS: 3

  ## TODO: Il nome di dominio a cui risponderà questa istanza di Discourse
  ## Obbligatorio. Discourse non funzionerà con un semplice numero IP.
  DISCOURSE_HOSTNAME: 'example.com'

  ## Rimuovi il commento se desideri che il contenitore venga avviato con lo stesso
  ## nome host (opzione -h) specificato sopra (predefinito "$hostname-$config")
  #DOCKER_USE_HOSTNAME: true

  ## TODO: Elenco di email separate da virgola che diventeranno amministratori e sviluppatori
  ## al primo esempio di registrazione 'user1@example.com,user2@example.com'
  DISCOURSE_DEVELOPER_EMAILS: 'test@mail.com'

  ## TODO: Il server SMTP utilizzato per convalidare nuovi account e inviare notifiche
  ## INDIRIZZO SMTP, nome utente e password sono obbligatori
  ## ATTENZIONE: il carattere '#' nella password SMTP può causare problemi!
  DISCOURSE_SMTP_ADDRESS: smtp.mail.io
  #DISCOURSE_SMTP_PORT: 587
  DISCOURSE_SMTP_USER_NAME: 111
  DISCOURSE_SMTP_PASSWORD: 111
  #DISCOURSE_SMTP_ENABLE_START_TLS: true           # (opzionale, valore predefinito true)
  #DISCOURSE_SMTP_DOMAIN: discourse.example.com    # (richiesto da alcuni provider)
  #DISCOURSE_NOTIFICATION_EMAIL: noreply@discourse.example.com    # (indirizzo da cui inviare le notifiche)

  ## Se hai aggiunto il template Lets Encrypt, rimuovi il commento qui sotto per ottenere un certificato SSL gratuito
  #LETSENCRYPT_ACCOUNT_EMAIL: me@example.com

  ## L'indirizzo CDN http o https per questa istanza di Discourse (configurato per l'acquisizione)
  ## consulta https://meta.discourse.org/t/14857 per i dettagli
  #DISCOURSE_CDN_URL: https://discourse-cdn.example.com
  
  ## La chiave IP di geolocalizzazione maxmind per la ricerca degli indirizzi IP
  ## consulta https://meta.discourse.org/t/-/137387/23 per i dettagli
  #DISCOURSE_MAXMIND_LICENSE_KEY: 1234567890123456

## Il contenitore Docker è senza stato; tutti i dati sono archiviati in /shared
volumes:
  - volume:
      host: /var/discourse/shared/standalone
      guest: /shared
  - volume:
      host: /var/discourse/shared/standalone/log/var-log
      guest: /var/log

## I plugin vanno qui
## consulta https://meta.discourse.org/t/19157 per i dettagli
hooks:
  after_code:
    - exec:
        cd: $home/plugins
        cmd:
          - git clone https://github.com/discourse/docker_manager.git

## Qualsiasi comando personalizzato da eseguire dopo la compilazione
run:
  - exec: echo "Inizio dei comandi personalizzati"
  ## Se desideri impostare l'indirizzo email 'From' per la tua prima registrazione, rimuovi il commento e modifica:
  ## Dopo aver ricevuto la prima email di iscrizione, rimetti il commento alla riga. Deve essere eseguito solo una volta.
  #- exec: rails r "SiteSetting.notification_email='info@unconfigured.discourse.org'"
  #- exec: chown -R discourse:discourse /var/www/discourse/tmp/cache/bootsnap  # esempio di comando su come ho provato a correggere i permessi dei file
  - exec: echo "Fine dei comandi personalizzati"

Non hai eseguito discourse-setup, vero? Dovrebbe aver definito alcune cose che hai commentato. Ho appena apportato quelle modifiche e voglio essere sicuro che funzionino come previsto.

C’è un motivo per cui non stai usando Let’s Encrypt?

Non vedo comunque una spiegazione per il tuo problema.

Innanzitutto, l’applicazione è stata creata utilizzando discourse-setup. Dopo alcuni tentativi di ricostruzione senza ottenere risultati positivi, ho fatto riferimento a una delle configurazioni .yml predefinite presenti nella directory /samples, modificandola poi semplicemente con le mie credenziali.
Perché non Let’s Encrypt? Mi è stato chiesto di utilizzare i certificati del client. Ma per quanto ne so, i certificati non c’entrano nulla, poiché sono validi e non causano alcun problema.
Il problema sembra essere a livello di progetto ed è specificamente legato ai permessi del file di cache di bootsnap (forse il problema risiede da parte di Bootsnap).

Grazie. Concordo sul fatto che non sia probabile che sia il problema. Ho eseguito un paio di installazioni ieri che hanno funzionato perfettamente. Non vedo alcuna spiegazione per il tuo problema.

Anche noi stavamo affrontando lo stesso problema e confermo che eseguire (all’interno del container Docker):

chown -R discourse:discourse /var/www/discourse/tmp

ha risolto il problema! Non sono stati necessari riavvii. Le autorizzazioni della directory ‘tmp’ erano assegnate a ‘discourse:www-data’ prima della modifica del proprietario. Speriamo che in futuro questo venga risolto, così da non dover più eseguire manualmente questa azione dopo ogni rebuild.

Stai eseguendo il launcher come root?

Sì, @pfaffman, lo sono. È questo il problema?

Non credo di sì. Avvio sempre le mie istanze self-hosted come root e non ho mai riscontrato un problema del genere.

Chi è il proprietario della directory se non usi chown? In un container recentemente ricostruito appare così:

# ls -l /var/www/discourse/tmp
total 36
lrwxrwxrwx 1 root      root         19 Mar  2 14:56 backups -> /shared/tmp/backups
drwxr-xr-x 1 discourse discourse  4096 Mar  2 14:57 cache
drwxr-xr-x 1 discourse discourse  4096 Mar  2 14:57 ember-rails
drwxr-xr-x 1 discourse root       4096 Mar  2 15:04 pids
lrwxrwxrwx 1 root      root         20 Mar  2 14:56 restores -> /shared/tmp/restores
drwxr-xr-x 2 discourse root       4096 Mar  2 14:56 sockets
drwxr-xr-x 2 discourse discourse 12288 Mar  2 15:02 stylesheet-cache

Hai aggiunto comandi o hook personalizzati al tuo app.yml oltre al clonaggio dei plugin?

Il proprietario utente e gruppo della directory /var/www/discourse/tmp era discourse:www-data dopo l’avvio del contenitore. Riassegnarlo a discourse:discourse ha risolto il problema. Questo non mi era mai successo prima, nonostante utilizzi Discourse da diversi mesi. Comunque, è stata una correzione semplice e potrebbe essere stato un caso isolato, quindi non voglio disturbarvi ulteriormente. Grazie mille @gerhard!