1use crate::ast::*;
17use crate::ty::TypeExpr;
18use std::fmt::Write;
19
20pub fn format(program: &Program) -> String {
22 let mut formatter = Formatter::new();
23 formatter.format_program(program);
24 formatter.output
25}
26
27struct Formatter {
28 output: String,
29 indent: usize,
30}
31
32impl Formatter {
33 fn new() -> Self {
34 Self {
35 output: String::new(),
36 indent: 0,
37 }
38 }
39
40 fn write(&mut self, s: &str) {
41 self.output.push_str(s);
42 }
43
44 fn writeln(&mut self, s: &str) {
45 self.write_indent();
46 self.output.push_str(s);
47 self.output.push('\n');
48 }
49
50 fn newline(&mut self) {
51 self.output.push('\n');
52 }
53
54 fn write_indent(&mut self) {
55 for _ in 0..self.indent {
56 self.output.push_str(" ");
57 }
58 }
59
60 fn indent(&mut self) {
61 self.indent += 1;
62 }
63
64 fn dedent(&mut self) {
65 self.indent = self.indent.saturating_sub(1);
66 }
67
68 fn format_program(&mut self, program: &Program) {
69 let mut first = true;
70
71 for m in &program.mod_decls {
73 if !first {
74 self.newline();
75 }
76 first = false;
77 self.format_mod_decl(m);
78 }
79
80 for u in &program.use_decls {
82 if !first {
83 self.newline();
84 }
85 first = false;
86 self.format_use_decl(u);
87 }
88
89 for c in &program.consts {
91 if !first {
92 self.newline();
93 }
94 first = false;
95 self.format_const_decl(c);
96 }
97
98 for r in &program.records {
100 if !first {
101 self.newline();
102 }
103 first = false;
104 self.format_record_decl(r);
105 }
106
107 for e in &program.enums {
109 if !first {
110 self.newline();
111 }
112 first = false;
113 self.format_enum_decl(e);
114 }
115
116 for t in &program.tools {
118 if !first {
119 self.newline();
120 }
121 first = false;
122 self.format_tool_decl(t);
123 }
124
125 for f in &program.functions {
127 if !first {
128 self.newline();
129 }
130 first = false;
131 self.format_fn_decl(f);
132 }
133
134 for a in &program.agents {
136 if !first {
137 self.newline();
138 }
139 first = false;
140 self.format_agent_decl(a);
141 }
142
143 for t in &program.tests {
145 if !first {
146 self.newline();
147 }
148 first = false;
149 self.format_test_decl(t);
150 }
151
152 if let Some(run_agent) = &program.run_agent {
154 if !first {
155 self.newline();
156 self.newline();
157 }
158 self.write("run ");
159 self.write(&run_agent.name);
160 self.writeln(";");
161 }
162 }
163
164 fn format_mod_decl(&mut self, m: &ModDecl) {
165 if m.is_pub {
166 self.write("pub ");
167 }
168 self.write("mod ");
169 self.write(&m.name.name);
170 self.writeln(";");
171 }
172
173 fn format_use_decl(&mut self, u: &UseDecl) {
174 if u.is_pub {
175 self.write("pub ");
176 }
177 self.write("use ");
178 self.write(
179 &u.path
180 .iter()
181 .map(|i| i.name.as_str())
182 .collect::<Vec<_>>()
183 .join("::"),
184 );
185 match &u.kind {
186 UseKind::Simple(alias) => {
187 if let Some(a) = alias {
188 self.write(" as ");
189 self.write(&a.name);
190 }
191 }
192 UseKind::Glob => {
193 self.write("::*");
194 }
195 UseKind::Group(names) => {
196 self.write("::{");
197 for (i, (name, alias)) in names.iter().enumerate() {
198 if i > 0 {
199 self.write(", ");
200 }
201 self.write(&name.name);
202 if let Some(a) = alias {
203 self.write(" as ");
204 self.write(&a.name);
205 }
206 }
207 self.write("}");
208 }
209 }
210 self.writeln(";");
211 }
212
213 fn format_const_decl(&mut self, c: &ConstDecl) {
214 if c.is_pub {
215 self.write("pub ");
216 }
217 self.write("const ");
218 self.write(&c.name.name);
219 self.write(": ");
220 self.format_type(&c.ty);
221 self.write(" = ");
222 self.format_expr(&c.value);
223 self.writeln(";");
224 }
225
226 fn format_record_decl(&mut self, r: &RecordDecl) {
227 if r.is_pub {
228 self.write("pub ");
229 }
230 self.write("record ");
231 self.write(&r.name.name);
232 self.write(" {\n");
233 self.indent();
234 for field in &r.fields {
235 self.write_indent();
236 self.write(&field.name.name);
237 self.write(": ");
238 self.format_type(&field.ty);
239 self.write("\n");
240 }
241 self.dedent();
242 self.writeln("}");
243 }
244
245 fn format_enum_decl(&mut self, e: &EnumDecl) {
246 if e.is_pub {
247 self.write("pub ");
248 }
249 self.write("enum ");
250 self.write(&e.name.name);
251 self.write(" {\n");
252 self.indent();
253 for variant in &e.variants {
254 self.write_indent();
255 self.write(&variant.name.name);
256 if let Some(payload) = &variant.payload {
257 self.write("(");
258 self.format_type(payload);
259 self.write(")");
260 }
261 self.write("\n");
262 }
263 self.dedent();
264 self.writeln("}");
265 }
266
267 fn format_tool_decl(&mut self, t: &ToolDecl) {
268 if t.is_pub {
269 self.write("pub ");
270 }
271 self.write("tool ");
272 self.write(&t.name.name);
273 self.write(" {\n");
274 self.indent();
275 for func in &t.functions {
276 self.write_indent();
277 self.write("fn ");
278 self.write(&func.name.name);
279 self.write("(");
280 for (i, param) in func.params.iter().enumerate() {
281 if i > 0 {
282 self.write(", ");
283 }
284 self.write(¶m.name.name);
285 self.write(": ");
286 self.format_type(¶m.ty);
287 }
288 self.write(") -> ");
289 self.format_type(&func.return_ty);
290 self.write("\n");
291 }
292 self.dedent();
293 self.writeln("}");
294 }
295
296 fn format_fn_decl(&mut self, f: &FnDecl) {
297 if f.is_pub {
298 self.write("pub ");
299 }
300 self.write("fn ");
301 self.write(&f.name.name);
302 self.write("(");
303 for (i, param) in f.params.iter().enumerate() {
304 if i > 0 {
305 self.write(", ");
306 }
307 self.write(¶m.name.name);
308 self.write(": ");
309 self.format_type(¶m.ty);
310 }
311 self.write(") -> ");
312 self.format_type(&f.return_ty);
313 if f.is_fallible {
314 self.write(" fails");
315 }
316 self.write(" {\n");
317 self.indent();
318 self.format_block(&f.body);
319 self.dedent();
320 self.writeln("}");
321 }
322
323 fn format_agent_decl(&mut self, agent: &AgentDecl) {
324 if agent.is_pub {
325 self.write("pub ");
326 }
327 self.write("agent ");
328 self.write(&agent.name.name);
329
330 if let Some(recv) = &agent.receives {
332 self.write(" receives ");
333 self.format_type(recv);
334 }
335
336 if !agent.tool_uses.is_empty() {
338 self.write(" uses ");
339 for (i, tool) in agent.tool_uses.iter().enumerate() {
340 if i > 0 {
341 self.write(", ");
342 }
343 self.write(&tool.name);
344 }
345 }
346
347 self.write(" {\n");
348 self.indent();
349
350 for belief in &agent.beliefs {
352 self.write_indent();
353 if belief.is_persistent {
354 self.write("@persistent ");
355 }
356 self.write(&belief.name.name);
357 self.write(": ");
358 self.format_type(&belief.ty);
359 self.write("\n");
360 }
361
362 if !agent.beliefs.is_empty() && !agent.handlers.is_empty() {
364 self.newline();
365 }
366
367 let mut sorted_handlers: Vec<&HandlerDecl> = agent.handlers.iter().collect();
369 sorted_handlers.sort_by_key(|h| match &h.event {
370 EventKind::Waking => 0,
371 EventKind::Start => 1,
372 EventKind::Message { .. } => 2,
373 EventKind::Pause => 3,
374 EventKind::Resume => 4,
375 EventKind::Error { .. } => 5,
376 EventKind::Stop => 6,
377 EventKind::Resting => 7,
378 });
379
380 for (i, handler) in sorted_handlers.iter().enumerate() {
381 if i > 0 {
382 self.newline();
383 }
384 self.format_handler(handler);
385 }
386
387 self.dedent();
388 self.writeln("}");
389 }
390
391 fn format_handler(&mut self, handler: &HandlerDecl) {
392 self.write_indent();
393 match &handler.event {
394 EventKind::Waking => {
395 self.write("on waking {\n");
396 }
397 EventKind::Start => {
398 self.write("on start {\n");
399 }
400 EventKind::Message {
401 param_name,
402 param_ty,
403 } => {
404 self.write("on message(");
405 self.write(¶m_name.name);
406 self.write(": ");
407 self.format_type(param_ty);
408 self.write(") {\n");
409 }
410 EventKind::Pause => {
411 self.write("on pause {\n");
412 }
413 EventKind::Resume => {
414 self.write("on resume {\n");
415 }
416 EventKind::Error { param_name } => {
417 self.write("on error(");
418 self.write(¶m_name.name);
419 self.write(": Error) {\n");
420 }
421 EventKind::Stop => {
422 self.write("on stop {\n");
423 }
424 EventKind::Resting => {
425 self.write("on resting {\n");
426 }
427 }
428 self.indent();
429 self.format_block(&handler.body);
430 self.dedent();
431 self.writeln("}");
432 }
433
434 fn format_test_decl(&mut self, t: &TestDecl) {
435 self.write("test \"");
436 for c in t.name.chars() {
437 match c {
438 '\\' => self.write("\\\\"),
439 '"' => self.write("\\\""),
440 '\n' => self.write("\\n"),
441 _ => self.output.push(c),
442 }
443 }
444 self.write("\" {\n");
445 self.indent();
446 self.format_block(&t.body);
447 self.dedent();
448 self.writeln("}");
449 }
450
451 fn format_block(&mut self, block: &Block) {
452 for stmt in &block.stmts {
453 self.format_stmt(stmt);
454 }
455 }
456
457 fn format_stmt(&mut self, stmt: &Stmt) {
458 match stmt {
459 Stmt::Let {
460 name, ty, value, ..
461 } => {
462 self.write_indent();
463 self.write("let ");
464 self.write(&name.name);
465 if let Some(t) = ty {
466 self.write(": ");
467 self.format_type(t);
468 }
469 self.write(" = ");
470 self.format_expr(value);
471 self.write(";\n");
472 }
473 Stmt::LetTuple {
474 names, ty, value, ..
475 } => {
476 self.write_indent();
477 self.write("let (");
478 for (i, name) in names.iter().enumerate() {
479 if i > 0 {
480 self.write(", ");
481 }
482 self.write(&name.name);
483 }
484 self.write(")");
485 if let Some(t) = ty {
486 self.write(": ");
487 self.format_type(t);
488 }
489 self.write(" = ");
490 self.format_expr(value);
491 self.write(";\n");
492 }
493 Stmt::Assign { name, value, .. } => {
494 self.write_indent();
495 self.write(&name.name);
496 self.write(" = ");
497 self.format_expr(value);
498 self.write(";\n");
499 }
500 Stmt::Expr { expr, .. } => {
501 self.write_indent();
502 self.format_expr(expr);
503 self.write(";\n");
504 }
505 Stmt::Return { value, .. } => {
506 self.write_indent();
507 self.write("return");
508 if let Some(v) = value {
509 self.write(" ");
510 self.format_expr(v);
511 }
512 self.write(";\n");
513 }
514 Stmt::While {
515 condition, body, ..
516 } => {
517 self.write_indent();
518 self.write("while ");
519 self.format_expr(condition);
520 self.write(" {\n");
521 self.indent();
522 self.format_block(body);
523 self.dedent();
524 self.writeln("}");
525 }
526 Stmt::For {
527 pattern,
528 iter,
529 body,
530 ..
531 } => {
532 self.write_indent();
533 self.write("for ");
534 self.format_pattern(pattern);
535 self.write(" in ");
536 self.format_expr(iter);
537 self.write(" {\n");
538 self.indent();
539 self.format_block(body);
540 self.dedent();
541 self.writeln("}");
542 }
543 Stmt::Loop { body, .. } => {
544 self.writeln("loop {");
545 self.indent();
546 self.format_block(body);
547 self.dedent();
548 self.writeln("}");
549 }
550 Stmt::Break { .. } => {
551 self.writeln("break;");
552 }
553 Stmt::SpanBlock { name, body, .. } => {
554 self.write_indent();
555 self.write("span ");
556 self.format_expr(name);
557 self.write(" {\n");
558 self.indent();
559 self.format_block(body);
560 self.dedent();
561 self.write_indent();
562 self.writeln("}");
563 }
564 Stmt::Checkpoint { .. } => {
565 self.write_indent();
566 self.writeln("checkpoint();");
567 }
568 Stmt::If {
569 condition,
570 then_block,
571 else_block,
572 ..
573 } => {
574 self.write_indent();
575 self.write("if ");
576 self.format_expr(condition);
577 self.write(" {\n");
578 self.indent();
579 self.format_block(then_block);
580 self.dedent();
581 self.write_indent();
582 self.write("}");
583 if let Some(else_b) = else_block {
584 self.write(" else ");
585 match else_b {
586 ElseBranch::ElseIf(if_stmt) => {
587 if let Stmt::If {
589 condition,
590 then_block,
591 else_block,
592 ..
593 } = if_stmt.as_ref()
594 {
595 self.write("if ");
596 self.format_expr(condition);
597 self.write(" {\n");
598 self.indent();
599 self.format_block(then_block);
600 self.dedent();
601 self.write_indent();
602 self.write("}");
603 if let Some(eb) = else_block {
604 self.format_else_branch(eb);
605 }
606 }
607 }
608 ElseBranch::Block(block) => {
609 self.write("{\n");
610 self.indent();
611 self.format_block(block);
612 self.dedent();
613 self.write_indent();
614 self.write("}");
615 }
616 }
617 }
618 self.write("\n");
619 }
620 Stmt::MockDivine { value, .. } => {
621 self.write_indent();
622 self.write("mock divine -> ");
623 self.format_mock_value(value);
624 self.write(";\n");
625 }
626 Stmt::MockTool {
627 tool_name,
628 fn_name,
629 value,
630 ..
631 } => {
632 self.write_indent();
633 self.write("mock tool ");
634 self.write(&tool_name.name);
635 self.write(".");
636 self.write(&fn_name.name);
637 self.write(" -> ");
638 self.format_mock_value(value);
639 self.write(";\n");
640 }
641 }
642 }
643
644 fn format_else_branch(&mut self, else_branch: &ElseBranch) {
645 self.write(" else ");
646 match else_branch {
647 ElseBranch::ElseIf(if_stmt) => {
648 if let Stmt::If {
649 condition,
650 then_block,
651 else_block,
652 ..
653 } = if_stmt.as_ref()
654 {
655 self.write("if ");
656 self.format_expr(condition);
657 self.write(" {\n");
658 self.indent();
659 self.format_block(then_block);
660 self.dedent();
661 self.write_indent();
662 self.write("}");
663 if let Some(eb) = else_block {
664 self.format_else_branch(eb);
665 }
666 }
667 }
668 ElseBranch::Block(block) => {
669 self.write("{\n");
670 self.indent();
671 self.format_block(block);
672 self.dedent();
673 self.write_indent();
674 self.write("}");
675 }
676 }
677 }
678
679 fn format_mock_value(&mut self, value: &MockValue) {
680 match value {
681 MockValue::Value(expr) => self.format_expr(expr),
682 MockValue::Fail(expr) => {
683 self.write("fail(");
684 self.format_expr(expr);
685 self.write(")");
686 }
687 }
688 }
689
690 fn format_pattern(&mut self, pattern: &Pattern) {
691 match pattern {
692 Pattern::Wildcard { .. } => self.write("_"),
693 Pattern::Binding { name, .. } => self.write(&name.name),
694 Pattern::Variant {
695 enum_name,
696 variant,
697 payload,
698 ..
699 } => {
700 if let Some(en) = enum_name {
701 self.write(&en.name);
702 self.write("::");
703 }
704 self.write(&variant.name);
705 if let Some(p) = payload {
706 self.write("(");
707 self.format_pattern(p);
708 self.write(")");
709 }
710 }
711 Pattern::Literal { value, .. } => self.format_literal(value),
712 Pattern::Tuple { elements, .. } => {
713 self.write("(");
714 for (i, p) in elements.iter().enumerate() {
715 if i > 0 {
716 self.write(", ");
717 }
718 self.format_pattern(p);
719 }
720 self.write(")");
721 }
722 }
723 }
724
725 fn format_expr(&mut self, expr: &Expr) {
726 match expr {
727 Expr::Literal { value, .. } => self.format_literal(value),
728 Expr::Var { name, .. } => self.write(&name.name),
729 Expr::Binary {
730 left, op, right, ..
731 } => {
732 self.format_expr(left);
733 self.write(" ");
734 self.write(&op.to_string());
735 self.write(" ");
736 self.format_expr(right);
737 }
738 Expr::Unary { op, operand, .. } => {
739 self.write(&op.to_string());
740 self.format_expr(operand);
741 }
742 Expr::Call { name, args, .. } => {
743 self.write(&name.name);
744 self.write("(");
745 for (i, arg) in args.iter().enumerate() {
746 if i > 0 {
747 self.write(", ");
748 }
749 self.format_expr(arg);
750 }
751 self.write(")");
752 }
753 Expr::Apply { callee, args, .. } => {
754 self.format_expr(callee);
755 self.write("(");
756 for (i, arg) in args.iter().enumerate() {
757 if i > 0 {
758 self.write(", ");
759 }
760 self.format_expr(arg);
761 }
762 self.write(")");
763 }
764 Expr::SelfMethodCall { method, args, .. } => {
765 self.write("self.");
766 self.write(&method.name);
767 self.write("(");
768 for (i, arg) in args.iter().enumerate() {
769 if i > 0 {
770 self.write(", ");
771 }
772 self.format_expr(arg);
773 }
774 self.write(")");
775 }
776 Expr::SelfField { field, .. } => {
777 self.write("self.");
778 self.write(&field.name);
779 }
780 Expr::FieldAccess { object, field, .. } => {
781 self.format_expr(object);
782 self.write(".");
783 self.write(&field.name);
784 }
785 Expr::TupleIndex { tuple, index, .. } => {
786 self.format_expr(tuple);
787 self.write(".");
788 let _ = write!(self.output, "{}", index);
789 }
790 Expr::List { elements, .. } => {
791 self.write("[");
792 for (i, elem) in elements.iter().enumerate() {
793 if i > 0 {
794 self.write(", ");
795 }
796 self.format_expr(elem);
797 }
798 self.write("]");
799 }
800 Expr::Tuple { elements, .. } => {
801 self.write("(");
802 for (i, elem) in elements.iter().enumerate() {
803 if i > 0 {
804 self.write(", ");
805 }
806 self.format_expr(elem);
807 }
808 if elements.len() == 1 {
809 self.write(",");
810 }
811 self.write(")");
812 }
813 Expr::RecordConstruct { name, fields, .. } => {
814 self.write(&name.name);
815 self.write(" { ");
816 for (i, field) in fields.iter().enumerate() {
817 if i > 0 {
818 self.write(", ");
819 }
820 self.write(&field.name.name);
821 self.write(": ");
822 self.format_expr(&field.value);
823 }
824 self.write(" }");
825 }
826 Expr::Map { entries, .. } => {
827 self.write("{");
828 for (i, entry) in entries.iter().enumerate() {
829 if i > 0 {
830 self.write(", ");
831 }
832 self.format_expr(&entry.key);
833 self.write(": ");
834 self.format_expr(&entry.value);
835 }
836 self.write("}");
837 }
838 Expr::VariantConstruct {
839 enum_name,
840 variant,
841 payload,
842 ..
843 } => {
844 self.write(&enum_name.name);
845 self.write(".");
846 self.write(&variant.name);
847 if let Some(p) = payload {
848 self.write("(");
849 self.format_expr(p);
850 self.write(")");
851 }
852 }
853 Expr::Match {
854 scrutinee, arms, ..
855 } => {
856 self.write("match ");
857 self.format_expr(scrutinee);
858 self.write(" {\n");
859 self.indent();
860 for arm in arms {
861 self.format_match_arm(arm);
862 }
863 self.dedent();
864 self.write_indent();
865 self.write("}");
866 }
867 Expr::Closure { params, body, .. } => {
868 self.write("|");
869 for (i, param) in params.iter().enumerate() {
870 if i > 0 {
871 self.write(", ");
872 }
873 self.write(¶m.name.name);
874 if let Some(ty) = ¶m.ty {
875 self.write(": ");
876 self.format_type(ty);
877 }
878 }
879 self.write("| ");
880 self.format_expr(body);
881 }
882 Expr::Paren { inner, .. } => {
883 self.write("(");
884 self.format_expr(inner);
885 self.write(")");
886 }
887 Expr::StringInterp { template, .. } => {
888 self.format_string_template(template);
889 }
890 Expr::Summon { agent, fields, .. } => {
891 self.write("summon ");
892 self.write(&agent.name);
893 if fields.is_empty() {
894 self.write(" {}");
895 } else if fields.len() <= 2 {
896 self.write(" { ");
897 for (i, field) in fields.iter().enumerate() {
898 if i > 0 {
899 self.write(", ");
900 }
901 self.write(&field.name.name);
902 self.write(": ");
903 self.format_expr(&field.value);
904 }
905 self.write(" }");
906 } else {
907 self.write(" {\n");
908 self.indent();
909 for field in fields {
910 self.write_indent();
911 self.write(&field.name.name);
912 self.write(": ");
913 self.format_expr(&field.value);
914 self.write(",\n");
915 }
916 self.dedent();
917 self.write_indent();
918 self.write("}");
919 }
920 }
921 Expr::Await {
922 handle, timeout, ..
923 } => {
924 self.write("await ");
925 self.format_expr(handle);
926 if let Some(t) = timeout {
927 self.write(" timeout(");
928 self.format_expr(t);
929 self.write(")");
930 }
931 }
932 Expr::Yield { value, .. } => {
933 self.write("yield(");
934 self.format_expr(value);
935 self.write(")");
936 }
937 Expr::Send {
938 handle, message, ..
939 } => {
940 self.write("send(");
941 self.format_expr(handle);
942 self.write(", ");
943 self.format_expr(message);
944 self.write(")");
945 }
946 Expr::Receive { .. } => {
947 self.write("receive()");
948 }
949 Expr::Divine {
950 template,
951 result_ty,
952 ..
953 } => {
954 self.write("divine(");
955 self.format_string_template(template);
956 if let Some(ty) = result_ty {
957 self.write(" -> ");
958 self.format_type(ty);
959 }
960 self.write(")");
961 }
962 Expr::Try { expr, .. } => {
963 self.write("try ");
964 self.format_expr(expr);
965 }
966 Expr::Catch {
967 expr,
968 error_bind,
969 recovery,
970 ..
971 } => {
972 self.format_expr(expr);
973 self.write(" catch");
974 if let Some(name) = error_bind {
975 self.write("(");
976 self.write(&name.name);
977 self.write(")");
978 }
979 self.write(" { ");
980 self.format_expr(recovery);
981 self.write(" }");
982 }
983 Expr::Fail { error, .. } => {
984 self.write("fail ");
985 self.format_expr(error);
986 }
987 Expr::Retry {
988 count, delay, body, ..
989 } => {
990 self.write("retry(");
991 self.format_expr(count);
992 if let Some(d) = delay {
993 self.write(", delay: ");
994 self.format_expr(d);
995 }
996 self.write(") {\n");
997 self.indent();
998 self.write_indent();
999 self.format_expr(body);
1000 self.write("\n");
1001 self.dedent();
1002 self.write_indent();
1003 self.write("}");
1004 }
1005 Expr::Trace { message, .. } => {
1006 self.write("trace(");
1007 self.format_expr(message);
1008 self.write(")");
1009 }
1010 Expr::ToolCall {
1011 tool,
1012 function,
1013 args,
1014 ..
1015 } => {
1016 self.write(&tool.name);
1017 self.write(".");
1018 self.write(&function.name);
1019 self.write("(");
1020 for (i, arg) in args.iter().enumerate() {
1021 if i > 0 {
1022 self.write(", ");
1023 }
1024 self.format_expr(arg);
1025 }
1026 self.write(")");
1027 }
1028 Expr::Reply { message, .. } => {
1029 self.write("reply(");
1030 self.format_expr(message);
1031 self.write(")");
1032 }
1033 }
1034 }
1035
1036 fn format_string_template(&mut self, template: &StringTemplate) {
1037 self.write("\"");
1038 for part in &template.parts {
1039 match part {
1040 StringPart::Literal(s) => {
1041 for c in s.chars() {
1042 match c {
1043 '\\' => self.write("\\\\"),
1044 '"' => self.write("\\\""),
1045 '\n' => self.write("\\n"),
1046 '\r' => self.write("\\r"),
1047 '\t' => self.write("\\t"),
1048 '{' => self.write("{{"),
1049 '}' => self.write("}}"),
1050 _ => self.output.push(c),
1051 }
1052 }
1053 }
1054 StringPart::Interpolation(expr) => {
1055 self.write("{");
1056 self.format_expr(expr);
1057 self.write("}");
1058 }
1059 }
1060 }
1061 self.write("\"");
1062 }
1063
1064 fn format_match_arm(&mut self, arm: &MatchArm) {
1065 self.write_indent();
1066 self.format_pattern(&arm.pattern);
1067 self.write(" => ");
1068 self.format_expr(&arm.body);
1069 self.write(",\n");
1070 }
1071
1072 fn format_literal(&mut self, lit: &Literal) {
1073 match lit {
1074 Literal::Int(n) => {
1075 let _ = write!(self.output, "{}", n);
1076 }
1077 Literal::Float(f) => {
1078 let _ = write!(self.output, "{}", f);
1079 }
1080 Literal::String(s) => {
1081 self.write("\"");
1082 for c in s.chars() {
1083 match c {
1084 '\\' => self.write("\\\\"),
1085 '"' => self.write("\\\""),
1086 '\n' => self.write("\\n"),
1087 '\r' => self.write("\\r"),
1088 '\t' => self.write("\\t"),
1089 _ => self.output.push(c),
1090 }
1091 }
1092 self.write("\"");
1093 }
1094 Literal::Bool(b) => {
1095 self.write(if *b { "true" } else { "false" });
1096 }
1097 }
1098 }
1099
1100 fn format_type(&mut self, ty: &TypeExpr) {
1101 match ty {
1102 TypeExpr::Int => self.write("Int"),
1103 TypeExpr::Float => self.write("Float"),
1104 TypeExpr::Bool => self.write("Bool"),
1105 TypeExpr::String => self.write("String"),
1106 TypeExpr::Unit => self.write("Unit"),
1107 TypeExpr::Error => self.write("Error"),
1108 TypeExpr::Named(name, type_args) => {
1109 self.write(&name.name);
1110 if !type_args.is_empty() {
1111 self.write("<");
1112 for (i, arg) in type_args.iter().enumerate() {
1113 if i > 0 {
1114 self.write(", ");
1115 }
1116 self.format_type(arg);
1117 }
1118 self.write(">");
1119 }
1120 }
1121 TypeExpr::List(inner) => {
1122 self.write("List<");
1123 self.format_type(inner);
1124 self.write(">");
1125 }
1126 TypeExpr::Option(inner) => {
1127 self.write("Option<");
1128 self.format_type(inner);
1129 self.write(">");
1130 }
1131 TypeExpr::Result(ok, err) => {
1132 self.write("Result<");
1133 self.format_type(ok);
1134 self.write(", ");
1135 self.format_type(err);
1136 self.write(">");
1137 }
1138 TypeExpr::Tuple(types) => {
1139 self.write("(");
1140 for (i, t) in types.iter().enumerate() {
1141 if i > 0 {
1142 self.write(", ");
1143 }
1144 self.format_type(t);
1145 }
1146 self.write(")");
1147 }
1148 TypeExpr::Oracle(inner) => {
1149 self.write("Oracle<");
1150 self.format_type(inner);
1151 self.write(">");
1152 }
1153 TypeExpr::Fn(params, ret) => {
1154 self.write("Fn(");
1155 for (i, p) in params.iter().enumerate() {
1156 if i > 0 {
1157 self.write(", ");
1158 }
1159 self.format_type(p);
1160 }
1161 self.write(") -> ");
1162 self.format_type(ret);
1163 }
1164 TypeExpr::Map(key, value) => {
1165 self.write("Map<");
1166 self.format_type(key);
1167 self.write(", ");
1168 self.format_type(value);
1169 self.write(">");
1170 }
1171 TypeExpr::Agent(name) => {
1172 self.write("Agent<");
1173 self.write(&name.name);
1174 self.write(">");
1175 }
1176 }
1177 }
1178}
1179
1180#[cfg(test)]
1181mod tests {
1182 use super::*;
1183 use crate::{lex, parse};
1184 use std::sync::Arc;
1185
1186 fn format_source(source: &str) -> String {
1187 let lex_result = lex(source).unwrap();
1188 let source_arc: Arc<str> = Arc::from(source);
1189 let (program, errors) = parse(lex_result.tokens(), source_arc);
1190 assert!(errors.is_empty(), "Parse errors: {:?}", errors);
1191 let program = program.unwrap();
1192 format(&program)
1193 }
1194
1195 #[test]
1196 fn test_format_simple_agent() {
1197 let source = r#"agent Greeter{name:String on start{print("Hello");emit(0);}}run Greeter;"#;
1198 let formatted = format_source(source);
1199 assert!(formatted.contains("agent Greeter {"));
1200 assert!(formatted.contains(" name: String"));
1201 assert!(formatted.contains(" on start {"));
1202 }
1203
1204 #[test]
1205 fn test_format_binary_operators() {
1206 let source = r#"agent Test{on start{let x=1+2*3;emit(x);}}run Test;"#;
1207 let formatted = format_source(source);
1208 assert!(formatted.contains("1 + 2 * 3"));
1209 }
1210}