golem_rib_repl/
repl_printer.rs

1// Copyright 2024-2025 Golem Cloud
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7//     http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
15use crate::rib_repl::ReplBootstrapError;
16use colored::Colorize;
17use rib::{RibError, RibResult};
18
19pub trait ReplPrinter {
20    fn print_rib_result(&self, result: &RibResult);
21    fn print_rib_error(&self, error: &RibError);
22    fn print_bootstrap_error(&self, error: &ReplBootstrapError);
23    fn print_runtime_error(&self, error: &str);
24}
25
26#[derive(Clone)]
27pub struct DefaultReplResultPrinter;
28
29impl ReplPrinter for DefaultReplResultPrinter {
30    fn print_rib_result(&self, result: &RibResult) {
31        println!("{}", result.to_string().green());
32    }
33
34    fn print_rib_error(&self, error: &RibError) {
35        match error {
36            RibError::InternalError(msg) => {
37                println!("{} {}", "[internal rib error]".red(), msg.red());
38            }
39            RibError::RibCompilationError(compilation_error) => {
40                let cause = &compilation_error.cause;
41                let position = compilation_error.expr.source_span().start_column();
42
43                println!("{}", "[compilation error]".red());
44                println!("{} {}", "position:".yellow(), position.to_string().white());
45                println!("{} {}", "cause:".yellow(), cause.white());
46
47                if !compilation_error.additional_error_details.is_empty() {
48                    for detail in &compilation_error.additional_error_details {
49                        println!("{}", detail.white());
50                    }
51                }
52
53                if !compilation_error.help_messages.is_empty() {
54                    for message in &compilation_error.help_messages {
55                        println!("{} {}", "help:".blue(), message.white());
56                    }
57                }
58            }
59            RibError::InvalidRibScript(script) => {
60                println!("{} {}", "[invalid script]".red(), script.white());
61            }
62        }
63    }
64
65    fn print_bootstrap_error(&self, error: &ReplBootstrapError) {
66        match error {
67            ReplBootstrapError::ReplHistoryFileError(msg) => {
68                println!("{} {}", "[warn]".yellow(), msg);
69            }
70            ReplBootstrapError::ComponentLoadError(msg) => {
71                println!("{} {}", "[error]".red(), msg);
72            }
73            ReplBootstrapError::MultipleComponentsFound(msg) => {
74                println!("{} {}", "[error]".red(), msg);
75                println!(
76                    "{}",
77                    "specify the component name when bootstrapping repl".yellow()
78                );
79            }
80            ReplBootstrapError::NoComponentsFound => {
81                println!(
82                    "{} no components found in the repl context",
83                    "[warn]".yellow()
84                );
85            }
86        }
87    }
88
89    fn print_runtime_error(&self, error: &str) {
90        println!("{} {}", "[runtime error]".red(), error.white());
91    }
92}