diff --git a/crates/wit-component/src/printing.rs b/crates/wit-component/src/printing.rs index 566aad004a..57ec8f1a4d 100644 --- a/crates/wit-component/src/printing.rs +++ b/crates/wit-component/src/printing.rs @@ -1,11 +1,16 @@ use anyhow::{anyhow, bail, Result}; use std::fmt::{self, Write}; +use std::mem; use wit_parser::*; /// A utility for printing WebAssembly interface definitions to a string. #[derive(Default)] pub struct WitPrinter { output: Output, + + // Count of how many items in this current block have been printed to print + // a blank line between each item, but not the first item. + any_items: bool, } impl WitPrinter { @@ -39,8 +44,16 @@ impl WitPrinter { Ok(std::mem::take(&mut self.output).into()) } + fn new_item(&mut self) { + if self.any_items { + self.output.push_str("\n"); + } + self.any_items = true; + } + /// Print the given WebAssembly interface to a string. fn print_interface(&mut self, resolve: &Resolve, id: InterfaceId) -> Result<()> { + let prev_items = mem::replace(&mut self.any_items, false); let interface = &resolve.interfaces[id]; self.print_types( @@ -52,16 +65,16 @@ impl WitPrinter { .map(|(name, id)| (name.as_str(), *id)), )?; - for (i, (name, func)) in interface.functions.iter().enumerate() { - if i > 0 { - self.output.push_str("\n"); - } + for (name, func) in interface.functions.iter() { + self.new_item(); self.print_name(name); self.output.push_str(": "); self.print_function(resolve, func)?; self.output.push_str("\n"); } + self.any_items = prev_items; + Ok(()) } @@ -108,8 +121,8 @@ impl WitPrinter { TypeOwner::World(id) => resolve.worlds[id].package.unwrap(), TypeOwner::None => unreachable!(), }; - let amt_to_import = types_to_import.len(); for (owner, tys) in types_to_import { + self.any_items = true; write!(&mut self.output, "use ")?; let id = match owner { TypeOwner::Interface(id) => id, @@ -134,11 +147,8 @@ impl WitPrinter { writeln!(&mut self.output, "}}")?; } - if amt_to_import > 0 && types_to_declare.len() > 0 { - self.output.push_str("\n"); - } - for id in types_to_declare { + self.new_item(); self.declare_type(resolve, &Type::Id(id))?; } @@ -182,6 +192,7 @@ impl WitPrinter { } fn print_world(&mut self, resolve: &Resolve, id: WorldId) -> Result<()> { + let prev_items = mem::replace(&mut self.any_items, false); let world = &resolve.worlds[id]; let pkgid = world.package.unwrap(); let mut types = Vec::new(); @@ -193,13 +204,21 @@ impl WitPrinter { }, _ => { self.print_world_item(resolve, name, import, pkgid, "import")?; + // Don't put a blank line between imports, but count + // imports as having printed something so if anything comes + // after them then a blank line is printed after imports. + self.any_items = true; } } } self.print_types(resolve, TypeOwner::World(id), types.into_iter())?; + if !world.exports.is_empty() { + self.new_item(); + } for (name, export) in world.exports.iter() { self.print_world_item(resolve, name, export, pkgid, "export")?; } + self.any_items = prev_items; Ok(()) } @@ -466,7 +485,7 @@ impl WitPrinter { self.print_name(name); self.output.push_str(" = "); self.print_type_name(resolve, inner)?; - self.output.push_str("\n\n"); + self.output.push_str("\n"); } None => bail!("unnamed type in document"), }, @@ -490,7 +509,7 @@ impl WitPrinter { self.print_name(name); self.output.push_str(" = "); self.print_handle_type(resolve, handle)?; - self.output.push_str("\n\n"); + self.output.push_str("\n"); Ok(()) } @@ -597,7 +616,7 @@ impl WitPrinter { self.print_type_name(resolve, &field.ty)?; self.output.push_str(",\n"); } - self.output.push_str("}\n\n"); + self.output.push_str("}\n"); Ok(()) } None => bail!("document has unnamed record type"), @@ -615,7 +634,7 @@ impl WitPrinter { self.print_name(name); self.output.push_str(" = "); self.print_tuple_type(resolve, tuple)?; - self.output.push_str("\n\n"); + self.output.push_str("\n"); } Ok(()) } @@ -630,7 +649,7 @@ impl WitPrinter { self.print_name(&flag.name); self.output.push_str(",\n"); } - self.output.push_str("}\n\n"); + self.output.push_str("}\n"); } None => bail!("document has unnamed flags type"), } @@ -659,7 +678,7 @@ impl WitPrinter { } self.output.push_str(",\n"); } - self.output.push_str("}\n\n"); + self.output.push_str("}\n"); Ok(()) } @@ -681,7 +700,7 @@ impl WitPrinter { self.print_type_name(resolve, &case.ty)?; self.output.push_str(",\n"); } - self.output.push_str("}\n\n"); + self.output.push_str("}\n"); Ok(()) } @@ -696,7 +715,7 @@ impl WitPrinter { self.print_name(name); self.output.push_str(" = "); self.print_option_type(resolve, payload)?; - self.output.push_str("\n\n"); + self.output.push_str("\n"); } Ok(()) } @@ -712,7 +731,7 @@ impl WitPrinter { self.print_name(name); self.output.push_str(" = "); self.print_result_type(resolve, result)?; - self.output.push_str("\n\n"); + self.output.push_str("\n"); } Ok(()) } @@ -729,7 +748,7 @@ impl WitPrinter { self.print_name(&case.name); self.output.push_str(",\n"); } - self.output.push_str("}\n\n"); + self.output.push_str("}\n"); Ok(()) } @@ -739,7 +758,7 @@ impl WitPrinter { self.print_name(name); self.output.push_str(" = list<"); self.print_type_name(resolve, ty)?; - self.output.push_str(">\n\n"); + self.output.push_str(">\n"); return Ok(()); } diff --git a/crates/wit-component/tests/components/adapt-export-reallocs/component.wit.print b/crates/wit-component/tests/components/adapt-export-reallocs/component.wit.print index d7e2f2b45a..183298fccf 100644 --- a/crates/wit-component/tests/components/adapt-export-reallocs/component.wit.print +++ b/crates/wit-component/tests/components/adapt-export-reallocs/component.wit.print @@ -4,5 +4,6 @@ world root { import new: interface { read: func(amt: u32) -> list } + export entrypoint: func(args: list) } diff --git a/crates/wit-component/tests/components/adapt-import-only-used-in-adapter/component.wit.print b/crates/wit-component/tests/components/adapt-import-only-used-in-adapter/component.wit.print index 0b750ef43b..5d06bd3474 100644 --- a/crates/wit-component/tests/components/adapt-import-only-used-in-adapter/component.wit.print +++ b/crates/wit-component/tests/components/adapt-import-only-used-in-adapter/component.wit.print @@ -3,6 +3,7 @@ package root:component world root { import foo:foo/adapter-imports import foo: func(x: string) + export bar: func() export adapter-bar: func(x: string) } diff --git a/crates/wit-component/tests/components/bare-funcs/component.wit.print b/crates/wit-component/tests/components/bare-funcs/component.wit.print index 91f1f83fca..34767c7ec0 100644 --- a/crates/wit-component/tests/components/bare-funcs/component.wit.print +++ b/crates/wit-component/tests/components/bare-funcs/component.wit.print @@ -3,6 +3,7 @@ package root:component world root { import foo: func() import bar: func() -> string + export baz: func() export foo2: func(x: string) -> option> } diff --git a/crates/wit-component/tests/components/ensure-default-type-exports/component.wit.print b/crates/wit-component/tests/components/ensure-default-type-exports/component.wit.print index ca7f581da4..f207bfb86b 100644 --- a/crates/wit-component/tests/components/ensure-default-type-exports/component.wit.print +++ b/crates/wit-component/tests/components/ensure-default-type-exports/component.wit.print @@ -2,5 +2,6 @@ package root:component world root { import foo:foo/foo + export a: func(b: u8) } diff --git a/crates/wit-component/tests/components/export-interface-using-import/component.wit.print b/crates/wit-component/tests/components/export-interface-using-import/component.wit.print index 22ea09e611..7e05cc1df5 100644 --- a/crates/wit-component/tests/components/export-interface-using-import/component.wit.print +++ b/crates/wit-component/tests/components/export-interface-using-import/component.wit.print @@ -2,6 +2,7 @@ package root:component world root { import foo:foo/foo + export x: interface { use foo:foo/foo.{r} } diff --git a/crates/wit-component/tests/components/export-name-shuffling/component.wit.print b/crates/wit-component/tests/components/export-name-shuffling/component.wit.print index 22943c96e2..801ed92221 100644 --- a/crates/wit-component/tests/components/export-name-shuffling/component.wit.print +++ b/crates/wit-component/tests/components/export-name-shuffling/component.wit.print @@ -4,6 +4,7 @@ world root { export foo:foo/name export name: interface { use foo:foo/name.{foo} + a: func(f: foo) } } diff --git a/crates/wit-component/tests/components/export-type-name-conflict/component.wit.print b/crates/wit-component/tests/components/export-type-name-conflict/component.wit.print index e25f5018e4..6622505e46 100644 --- a/crates/wit-component/tests/components/export-type-name-conflict/component.wit.print +++ b/crates/wit-component/tests/components/export-type-name-conflict/component.wit.print @@ -2,8 +2,10 @@ package root:component world root { import foo:foo/foo + export bar: interface { use foo:foo/foo.{foo as bar} + foo: func() -> bar } } diff --git a/crates/wit-component/tests/components/import-export-same-iface-name/component.wit.print b/crates/wit-component/tests/components/import-export-same-iface-name/component.wit.print index 72d127d09d..2841ebd4da 100644 --- a/crates/wit-component/tests/components/import-export-same-iface-name/component.wit.print +++ b/crates/wit-component/tests/components/import-export-same-iface-name/component.wit.print @@ -3,5 +3,6 @@ package root:component world root { import foo:dep/the-name import foo:foo/the-name + export foo:foo/the-name } diff --git a/crates/wit-component/tests/components/import-export/component.wit.print b/crates/wit-component/tests/components/import-export/component.wit.print index 37c6cbd6f7..8121619df0 100644 --- a/crates/wit-component/tests/components/import-export/component.wit.print +++ b/crates/wit-component/tests/components/import-export/component.wit.print @@ -4,6 +4,7 @@ world root { import foo: interface { a: func() -> string } + export bar: interface { a: func() diff --git a/crates/wit-component/tests/components/import-in-adapter-and-main-module/component.wit.print b/crates/wit-component/tests/components/import-in-adapter-and-main-module/component.wit.print index 2958d7c112..f4c5c50a23 100644 --- a/crates/wit-component/tests/components/import-in-adapter-and-main-module/component.wit.print +++ b/crates/wit-component/tests/components/import-in-adapter-and-main-module/component.wit.print @@ -5,10 +5,12 @@ world root { import foo:shared-dependency/types import main-dep: interface { use foo:shared-dependency/types.{a-typedef} + foo: func() -> a-typedef } import adapter-dep: interface { use foo:shared-dependency/types.{a-typedef} + foo: func() -> a-typedef } } diff --git a/crates/wit-component/tests/components/many-same-names/component.wit.print b/crates/wit-component/tests/components/many-same-names/component.wit.print index 9d04a8954c..91dc87f978 100644 --- a/crates/wit-component/tests/components/many-same-names/component.wit.print +++ b/crates/wit-component/tests/components/many-same-names/component.wit.print @@ -2,9 +2,11 @@ package root:component world root { import foo:foo/name + export foo:foo/name export name: interface { use foo:foo/name.{r2} + a: func() } } diff --git a/crates/wit-component/tests/components/rename-interface/component.wit.print b/crates/wit-component/tests/components/rename-interface/component.wit.print index 7d8c3347fa..8687ef18c3 100644 --- a/crates/wit-component/tests/components/rename-interface/component.wit.print +++ b/crates/wit-component/tests/components/rename-interface/component.wit.print @@ -4,6 +4,7 @@ world root { import foo:foo/foo import other-name: interface { use foo:foo/foo.{bar} + a: func() -> bar } } diff --git a/crates/wit-component/tests/components/tricky-order/component.wit.print b/crates/wit-component/tests/components/tricky-order/component.wit.print index 0bc89ae660..53365cc682 100644 --- a/crates/wit-component/tests/components/tricky-order/component.wit.print +++ b/crates/wit-component/tests/components/tricky-order/component.wit.print @@ -3,6 +3,7 @@ package root:component world root { import foo:foo/name1 import foo:foo/name2 + export name: interface { use foo:foo/name1.{name} use foo:foo/name2.{name as name1} diff --git a/crates/wit-component/tests/components/worlds-with-type-renamings/component.wit.print b/crates/wit-component/tests/components/worlds-with-type-renamings/component.wit.print index de1389d4bf..b87bb226f9 100644 --- a/crates/wit-component/tests/components/worlds-with-type-renamings/component.wit.print +++ b/crates/wit-component/tests/components/worlds-with-type-renamings/component.wit.print @@ -3,5 +3,6 @@ package root:component world root { import foo:foo/i use foo:foo/i.{some-type as other-name} + export foo:foo/i } diff --git a/crates/wit-component/tests/interfaces/diamond-disambiguate/foo.wit.print b/crates/wit-component/tests/interfaces/diamond-disambiguate/foo.wit.print index 4856804be2..50986fedb2 100644 --- a/crates/wit-component/tests/interfaces/diamond-disambiguate/foo.wit.print +++ b/crates/wit-component/tests/interfaces/diamond-disambiguate/foo.wit.print @@ -2,12 +2,10 @@ package foo:foo interface shared2 { type t2 = u8 - } interface shared1 { type t1 = u8 - } world w1 { diff --git a/crates/wit-component/tests/interfaces/diamond.wit.print b/crates/wit-component/tests/interfaces/diamond.wit.print index 71bfcefb7d..9972b21323 100644 --- a/crates/wit-component/tests/interfaces/diamond.wit.print +++ b/crates/wit-component/tests/interfaces/diamond.wit.print @@ -4,11 +4,11 @@ interface shared-items { enum the-enum { a, } - } world w3 { import shared-items + export bar: interface { use shared-items.{the-enum} } @@ -18,6 +18,7 @@ world w2 { import foo: interface { use shared-items.{the-enum} } + export bar: interface { use shared-items.{the-enum} } diff --git a/crates/wit-component/tests/interfaces/empty.wit.print b/crates/wit-component/tests/interfaces/empty.wit.print index 44b9e27e6b..4f16a4b9f0 100644 --- a/crates/wit-component/tests/interfaces/empty.wit.print +++ b/crates/wit-component/tests/interfaces/empty.wit.print @@ -7,6 +7,7 @@ world empty-world { import empty import empty: interface { } + export empty export empty2: interface { } diff --git a/crates/wit-component/tests/interfaces/import-and-export.wit.print b/crates/wit-component/tests/interfaces/import-and-export.wit.print index 3aabe67040..4dbc26b837 100644 --- a/crates/wit-component/tests/interfaces/import-and-export.wit.print +++ b/crates/wit-component/tests/interfaces/import-and-export.wit.print @@ -10,5 +10,6 @@ interface bar { world import-and-export { import foo + export bar } diff --git a/crates/wit-component/tests/interfaces/multi-doc/foo.wit.print b/crates/wit-component/tests/interfaces/multi-doc/foo.wit.print index ef482f6205..c72e2d06b5 100644 --- a/crates/wit-component/tests/interfaces/multi-doc/foo.wit.print +++ b/crates/wit-component/tests/interfaces/multi-doc/foo.wit.print @@ -3,7 +3,6 @@ package foo:foo interface b { record the-type { } - } interface b2 { diff --git a/crates/wit-component/tests/interfaces/multiple-use.wit.print b/crates/wit-component/tests/interfaces/multiple-use.wit.print index 3284d8d950..30455eada6 100644 --- a/crates/wit-component/tests/interfaces/multiple-use.wit.print +++ b/crates/wit-component/tests/interfaces/multiple-use.wit.print @@ -4,12 +4,10 @@ interface foo { type t2 = u8 type t1 = u8 - } interface bar { type u = u8 - } interface baz { diff --git a/crates/wit-component/tests/interfaces/pkg-use-chain/chain.wit.print b/crates/wit-component/tests/interfaces/pkg-use-chain/chain.wit.print index ccff4b179a..6d3e94c9eb 100644 --- a/crates/wit-component/tests/interfaces/pkg-use-chain/chain.wit.print +++ b/crates/wit-component/tests/interfaces/pkg-use-chain/chain.wit.print @@ -2,7 +2,6 @@ package foo:chain interface a { type a = u8 - } interface def { @@ -11,7 +10,6 @@ interface def { enum name { other, } - } interface foo { diff --git a/crates/wit-component/tests/interfaces/pkg-use-chain2/foo.wit.print b/crates/wit-component/tests/interfaces/pkg-use-chain2/foo.wit.print index 5dd138c089..02a7f1a3f5 100644 --- a/crates/wit-component/tests/interfaces/pkg-use-chain2/foo.wit.print +++ b/crates/wit-component/tests/interfaces/pkg-use-chain2/foo.wit.print @@ -3,7 +3,6 @@ package foo:foo interface other { record name { } - } interface bar { @@ -12,7 +11,6 @@ interface bar { enum name { a, } - } interface foo { diff --git a/crates/wit-component/tests/interfaces/print-keyword.wit.print b/crates/wit-component/tests/interfaces/print-keyword.wit.print index ed797422d1..4488715b75 100644 --- a/crates/wit-component/tests/interfaces/print-keyword.wit.print +++ b/crates/wit-component/tests/interfaces/print-keyword.wit.print @@ -8,6 +8,5 @@ interface %interface { record %record { %variant: %world, } - } diff --git a/crates/wit-component/tests/interfaces/records.wit.print b/crates/wit-component/tests/interfaces/records.wit.print index 630dea861e..34da243b10 100644 --- a/crates/wit-component/tests/interfaces/records.wit.print +++ b/crates/wit-component/tests/interfaces/records.wit.print @@ -58,5 +58,6 @@ interface records { world records-world { import records + export records } diff --git a/crates/wit-component/tests/interfaces/simple-use.wit.print b/crates/wit-component/tests/interfaces/simple-use.wit.print index 99ec8690f0..00b4d1e1cf 100644 --- a/crates/wit-component/tests/interfaces/simple-use.wit.print +++ b/crates/wit-component/tests/interfaces/simple-use.wit.print @@ -5,11 +5,11 @@ interface types { info, debug, } - } interface console { use types.{level} + log: func(level: level, msg: string) } diff --git a/crates/wit-component/tests/interfaces/type-alias.wit.print b/crates/wit-component/tests/interfaces/type-alias.wit.print index ceb42db28c..6d9300cc17 100644 --- a/crates/wit-component/tests/interfaces/type-alias.wit.print +++ b/crates/wit-component/tests/interfaces/type-alias.wit.print @@ -10,5 +10,6 @@ interface foo { world my-world { import foo + export foo } diff --git a/crates/wit-component/tests/interfaces/use-chain.wit.print b/crates/wit-component/tests/interfaces/use-chain.wit.print index 902f62fd82..fc19fb45ab 100644 --- a/crates/wit-component/tests/interfaces/use-chain.wit.print +++ b/crates/wit-component/tests/interfaces/use-chain.wit.print @@ -6,7 +6,6 @@ interface foo { type b = a type c = b - } interface bar { diff --git a/crates/wit-component/tests/interfaces/use-for-type.wit.print b/crates/wit-component/tests/interfaces/use-for-type.wit.print index 001dd2dca1..9659920938 100644 --- a/crates/wit-component/tests/interfaces/use-for-type.wit.print +++ b/crates/wit-component/tests/interfaces/use-for-type.wit.print @@ -5,7 +5,6 @@ interface foo { interface bar { type t = u8 - } interface baz { @@ -14,6 +13,5 @@ interface baz { record bar { a: t, } - } diff --git a/crates/wit-component/tests/interfaces/wasi-http/http.wit.print b/crates/wit-component/tests/interfaces/wasi-http/http.wit.print index 5ad1f984a8..29e047d157 100644 --- a/crates/wit-component/tests/interfaces/wasi-http/http.wit.print +++ b/crates/wit-component/tests/interfaces/wasi-http/http.wit.print @@ -129,11 +129,13 @@ interface types { interface outgoing-handler { use types.{outgoing-request, request-options, future-incoming-response} + handle: func(request: outgoing-request, options: option) -> future-incoming-response } interface incoming-handler { use types.{incoming-request, response-outparam} + handle: func(request: incoming-request, response-out: response-outparam) } @@ -144,5 +146,6 @@ world proxy { import wasi:io/streams import types import outgoing-handler + export incoming-handler } diff --git a/crates/wit-component/tests/interfaces/world-inline-interface.wit.print b/crates/wit-component/tests/interfaces/world-inline-interface.wit.print index 780ad00717..ede6fa0abd 100644 --- a/crates/wit-component/tests/interfaces/world-inline-interface.wit.print +++ b/crates/wit-component/tests/interfaces/world-inline-interface.wit.print @@ -3,6 +3,7 @@ package foo:foo world has-inline { import foo: interface { } + export bar: interface { } } diff --git a/crates/wit-component/tests/interfaces/world-pkg-conflict/foo.wit.print b/crates/wit-component/tests/interfaces/world-pkg-conflict/foo.wit.print index 2cee9337ae..ffc2995e97 100644 --- a/crates/wit-component/tests/interfaces/world-pkg-conflict/foo.wit.print +++ b/crates/wit-component/tests/interfaces/world-pkg-conflict/foo.wit.print @@ -2,7 +2,6 @@ package foo:foo interface a { type t = u32 - } interface foo { diff --git a/crates/wit-component/tests/interfaces/world-top-level.wit.print b/crates/wit-component/tests/interfaces/world-top-level.wit.print index 40fd90e71d..729c8d1f03 100644 --- a/crates/wit-component/tests/interfaces/world-top-level.wit.print +++ b/crates/wit-component/tests/interfaces/world-top-level.wit.print @@ -11,6 +11,7 @@ world foo { } import foo: func() import bar: func(arg: u32) + export another-interface: interface { } export foo2: func() diff --git a/crates/wit-component/tests/interfaces/worlds-with-types.wit.print b/crates/wit-component/tests/interfaces/worlds-with-types.wit.print index f71ab16292..28c25e4f78 100644 --- a/crates/wit-component/tests/interfaces/worlds-with-types.wit.print +++ b/crates/wit-component/tests/interfaces/worlds-with-types.wit.print @@ -2,17 +2,18 @@ package foo:foo interface import-me { type foo = u32 - } world with-imports { import import-me import a: func(a: foo) use import-me.{foo} + export b: func(a: foo) } world simple { import a: func(a: foo) -> bar + record foo { } diff --git a/crates/wit-component/tests/merge/success/merge/foo.wit b/crates/wit-component/tests/merge/success/merge/foo.wit index 3892251b03..2081f327ec 100644 --- a/crates/wit-component/tests/merge/success/merge/foo.wit +++ b/crates/wit-component/tests/merge/success/merge/foo.wit @@ -10,7 +10,6 @@ interface shared-only-into { interface shared-items { type a = u32 - } interface only-into { @@ -41,6 +40,7 @@ world shared-world { import shared-items import d: interface { } + type c = u32 export shared-items diff --git a/crates/wit-component/tests/merge/success/merge/from.wit b/crates/wit-component/tests/merge/success/merge/from.wit index 8720527126..3561136b84 100644 --- a/crates/wit-component/tests/merge/success/merge/from.wit +++ b/crates/wit-component/tests/merge/success/merge/from.wit @@ -2,6 +2,7 @@ package foo:%from interface a { use foo:foo/only-from.{r} + foo: func() } diff --git a/crates/wit-component/tests/merge/success/merge/into.wit b/crates/wit-component/tests/merge/success/merge/into.wit index 55e4b952e0..4e61e7f5c4 100644 --- a/crates/wit-component/tests/merge/success/merge/into.wit +++ b/crates/wit-component/tests/merge/success/merge/into.wit @@ -2,6 +2,7 @@ package foo:into interface b { use foo:foo/only-into.{r} + foo: func() } diff --git a/crates/wit-component/tests/merge/success/merge/only-from-dep.wit b/crates/wit-component/tests/merge/success/merge/only-from-dep.wit index fa8b3336ef..3381d36cda 100644 --- a/crates/wit-component/tests/merge/success/merge/only-from-dep.wit +++ b/crates/wit-component/tests/merge/success/merge/only-from-dep.wit @@ -2,6 +2,5 @@ package foo:only-from-dep interface a { type a = u32 - }