Attention: Here be dragons
This is the latest
(unstable) version of this documentation, which may document features
not available in or compatible with released stable versions of Godot.
Checking the stable version of the documentation...
Logging
Godot offre diversi modi per organizzare e recuperare i messaggi di log.
Stampare i messaggi
Vedi anche
Consultare Stampare i messaggi per istruzioni sulla stampa dei messaggi. L'output stampato è generalmente identico a quello registrato.
Quando si esegue un progetto dall'editor, l'editor visualizzerà il testo registrato nel Pannello Output.
Impostazioni del progetto
Ci sono varie impostazioni del progetto che controllano il comportamento di logging in Godot:
Application > Run > Disable stdout: Disables logging to standard output entirely. This also affects what custom loggers receive. This can be controlled at runtime by setting Engine.print_to_stdout.
Application > Run > Disable stderr: Disables logging to standard error entirely. This also affects what custom loggers receive. This can be controlled at runtime by setting Engine.print_error_messages.
Debug > Settings > stdout > Verbose stdout: Enables verbose logging to standard output. Prints from print_verbose() are only visible if verbose mode is enabled.
Debug > Impostazioni > stdout > Stampa FPS: Stampa i frame al secondo ogni secondo, nonché lo stato del V-Sync all'avvio (poiché può effettivamente limitare la frequenza massima dei frame).
Debug > Impostazioni > stdout > Stampa profilo GPU: Stampa un report sull'utilizzo della GPU ogni secondo, attraverso la stessa origine dati di Profiler visivo.
È possibile anche sovrascrivere alcune di queste impostazioni del progetto attraverso gli argomenti della riga di comando come --quiet, --verbose e --print-fps.
Anche il logging su file del motore è configurabile, come descritto nella sezione seguente.
Logging integrato su file
Come predefinito, Godot scrive i file di log in user://logs/godot.log sulle piattaforme desktop. È possibile modificare questa posizione modificando l'impostazione del progetto debug/file_logging/log_path. I log vengono ruotati per mantenere i file più vecchi disponibili per l'ispezione. Ogni sessione crea un nuovo file di log, con il vecchio file rinominato per contenere la data in cui è stato ruotato. Come predefinito, sono conservati fino a 5 file di log, il che è possibile regolare attraverso l'impostazione del progetto debug/file_logging/max_log_files.
È possibile anche disattivare il logging su file completamente attraverso l'impostazione del progetto debug/file_logging/enable_file_logging.
Quando il progetto si blocca, i log dei crash vengono scritti nello stesso file del file di log. Il log dei crash conterrà un backtrace utilizzabile solo se il binario eseguito contiene simboli di debug, o se riesce a trovare un file di simboli di debug corrispondente al binario. I binari ufficiali non forniscono simboli di debug, quindi è necessaria una build personalizzata per funzionare. Consultare Simboli di debug per istruzioni sulla compilazione di binari con i simboli di debug abilitati.
Nota
I file di log per le istruzioni print() sono aggiornati quando l'output standard viene svuotato dal motore. L'output standard viene svuotato a ogni stampa solo nelle build di debug. Nei progetti esportati in modalità rilascio, l'output standard viene svuotato solo quando il progetto si chiude o si blocca per migliorare le prestazioni, soprattutto se il progetto stampa spesso testo sull'output standard.
D'altro parte, il flusso di errore standard (utilizzato da printerr(), push_error() e push_warning()) viene sempre svuotato a ogni stampa, anche nei progetti esportati in modalità rilascio.
Per alcuni casi d'uso, come i server dedicati, può essere preferibile che le build di rilascio svuotino sempre lo stdout durante la stampa, così che i servizi di logging come journald possano raccogliere i log mentre il processo è in esecuzione. Ciò si può ottenere abilitando application/run/flush_stdout_on_print nelle Impostazioni del progetto.
Backtrace di script
A partire da Godot 4.5, quando il codice GDScript incontra un errore, registra un backtrace che punta all'origine dell'errore, contenendo anche il stack di chiamate che lo ha generato. Questo comportamento è sempre abilitato durante l'esecuzione nell'editor o quando il progetto è esportato in modalità debug.
Nei progetti esportati in modalità rilascio, i backtrace sono normalmente disabilitati per motivi di prestazioni. È possibile abilitarli selezionando Debug > Impostazioni > GDScript > Traccia sempre stack di chiamate nelle Impostazioni del progetto. Se si utilizza un sistema di log personalizzato che segnala le eccezioni a un servizio remoto, si consiglia di abilitarlo per rendere più fruibili gli errori segnalati.
Backtrace dei crash
Avvertimento
I backtrace dei crash sono utili solo se registrati in una build che contiene simboli di debug. I binari ufficiali di Godot non contengono simboli di debug, quindi è necessario compilare un binario personalizzato dell'editor o di un modello d'esportazione per ottenere utili backtrace dei crash.
Quando il progetto si blocca, viene visualizzato un backtrace del crash nel flusso di errore standard. Ecco come potrebbe apparire in una build con simboli di debug:
================================================================
handle_crash: Program crashed with signal 4
Engine version: Godot Engine v4.5.beta.custom_build (6c9aa4c7d3b9b91cd50714c40eeb234874df7075)
Dumping the backtrace. Please include this when reporting the bug to the project developer.
[1] /lib64/libc.so.6(+0x1a070) [0x7f6e5e277070] (??:0)
[2] godot() [0x4da3358] (/path/to/godot/core/core_bind.cpp:336 (discriminator 2))
[3] godot() [0xdf5f2f] (/path/to/godot/modules/gdscript/gdscript.h:591)
[4] godot() [0xbffd46] (/path/to/godot/modules/gdscript/gdscript.cpp:2065 (discriminator 1))
[5] godot() [0x30f2ea4] (/path/to/godot/core/variant/variant.h:870)
[6] godot() [0x550d4e1] (/path/to/godot/core/object/object.cpp:933)
[7] godot() [0x30d996a] (/path/to/godot/scene/main/node.cpp:318 (discriminator 1))
[8] godot() [0x3131a7f] (/path/to/godot/core/templates/hash_map.h:465)
[9] godot() [0x424589] (/path/to/godot/platform/linuxbsd/os_linuxbsd.cpp:970)
[10] /lib64/libc.so.6(+0x3575) [0x7f6e5e260575] (??:0)
[11] /lib64/libc.so.6(__libc_start_main+0x88) [0x7f6e5e260628] (??:0)
[12] godot() [0x464df5] (??:?)
-- END OF C++ BACKTRACE --
================================================================
GDScript backtrace (most recent call first):
[0] _ready (res://test.gd:5)
-- END OF GDSCRIPT BACKTRACE --
================================================================
D'altro canto, senza simboli di debug, apparirà simile a questo:
================================================================
handle_crash: Program crashed with signal 4
Engine version: Godot Engine v4.5.beta.custom_build (6c9aa4c7d3b9b91cd50714c40eeb234874df7075)
Dumping the backtrace. Please include this when reporting the bug to the project developer.
[1] /lib64/libc.so.6(+0x1a070) [0x7fdfaf666070] (??:0)
[2] godot() [0x4da3358] (??:0)
[3] godot() [0xdf5f2f] (??:0)
[4] godot() [0xbffd46] (??:0)
[5] godot() [0x30f2ea4] (??:0)
[6] godot() [0x550d4e1] (??:0)
[7] godot() [0x30d996a] (??:0)
[8] godot() [0x3131a7f] (??:0)
[9] godot() [0x424589] (??:0)
[10] /lib64/libc.so.6(+0x3575) [0x7fdfaf64f575] (??:0)
[11] /lib64/libc.so.6(__libc_start_main+0x88) [0x7fdfaf64f628] (??:0)
[12] godot() [0x464df5] (??:0)
-- END OF C++ BACKTRACE --
================================================================
GDScript backtrace (most recent call first):
[0] _ready (res://test.gd:5)
-- END OF GDSCRIPT BACKTRACE --
================================================================
Questo backtrace viene registrato anche nel file per la sessione attuale, ma non è visibile nel pannello Output nell'editor. Poiché il sistema di scripting del motore non è più in esecuzione quando il motore si blocca, non è possibile accedervi tramite scripting nella stessa sessione. Tuttavia, è comunque possibile leggere il backtrace del crash nella sessione successiva, caricando i file di log e cercando la stringa del backtrace del crash (Program crashed with signal) tramite FileAccess. Questo consente di accedere alle informazioni del backtrace anche dopo un crash, purché l'utente riavvii il progetto e il logging su file sia abilitata:
# This script can be made an autoload, so that it runs when the project starts.
extends Node
func _ready() -> void:
var log_dir: String = String(ProjectSettings.get_setting("debug/file_logging/log_path")).get_base_dir()
# Get the last log file by alphabetical order.
# Since the timestamp is featured in the file name, it should always be the most recent
# log file that was rotated. The non-timestamped log file is for the current session,
# so we don't want to read that one.
var last_log_file: String = log_dir.path_join(DirAccess.get_files_at(log_dir)[-1])
var last_long_contents: String = FileAccess.get_file_as_string(last_log_file)
var crash_begin_idx: int = last_long_contents.find("Program crashed with signal")
if crash_begin_idx != -1:
print("The previous session has crashed with the following backtrace:\n")
print(last_long_contents.substr(crash_begin_idx))
È possibile personalizzare il messaggio mostrato in cima al backtrace attraverso l'impostazione del progetto Debug > Impostazioni > Gestore arresti anomali > Messaggio. Questa impostazione può servire per indirizzare gli utenti a un URL o a un indirizzo email a cui segnalare eventuali problemi.
Creare logger personalizzati
A partire da Godot 4.5, è possibile creare logger personalizzati. Un logging personalizzato può servire a diversi scopi:
Mostrare una console di gioco con gli stessi messaggi stampati dal motore, senza richiedere la modifica di altri script.
Segnalare gli errori stampati dal computer del giocatore a un server remoto. Questo può rendere più facile correggere bug per gli sviluppatori quando il gioco è già stato rilasciato o durante i playtest.
Integrare un'esportazione di server dedicato con piattaforme di monitoraggio.
È possibile registrare un logger personalizzato creando una classe che eredita da Logger, poi passando un'istanza di questa classe a OS.add_logger, nel metodo _init() di uno script. Un buon punto per farlo è in un autoload.
La classe deve definire due metodi: _log_message() e _log_error().
Here is a minimal working example of a custom logger, with the script added as an autoload:
extends Node
class CustomLogger extends Logger:
# Note that this method is not called for messages that use
# `push_error()` and `push_warning()`, even though these are printed to stderr.
func _log_message(message: String, error: bool) -> void:
# Do something with `message`.
# `error` is `true` for messages printed to the standard error stream (stderr) with `print_error()`.
# Note that this method will be called from threads other than the main thread, possibly at the same
# time, so you will need to have some kind of thread-safety as part of it, like a Mutex.
pass
func _log_error(
function: String,
file: String,
line: int,
code: String,
rationale: String,
editor_notify: bool,
error_type: int,
script_backtraces: Array[ScriptBacktrace]
) -> void:
# Do something with the error. The error text is in `rationale`.
# See the Logger class reference for details on other parameters.
# Note that this method will be called from threads other than the main thread, possibly at the same
# time, so you will need to have some kind of thread-safety as part of it, like a Mutex.
pass
# Use `_init()` to initialize the logger as early as possible, which ensures that messages
# printed early are taken into account. However, even when using `_init()`, the engine's own
# initialization messages are not accessible.
func _init() -> void:
OS.add_logger(CustomLogger.new())
Si noti che per evitare una ricorsione infinita, non è possibile effettivamente utilizzare print() e i metodi correlati in _log_message(). Non è inoltre possibile utilizzare effettivamente push_error() o push_warning() in _log_error(). Tentando di farlo, verrà stampato un messaggio sullo stesso flusso del messaggio originale. Questo messaggio non è disponibile nel logger personalizzato, il che impedisce una ricorsione infinita:
While attempting to print a message, another message was printed:
...
While attempting to print an error, another error was printed:
...
Vedi anche
È possibile trovare un esempio di una console di gioco creata con un logger personalizzato nel Progetto demo Custom Logging.