---
# System prepended metadata

title: Component WIT

---

Current grammar:
```ebnf
       component-def ::= 'component' id '{' component-def-items* '}' .
 component-def-items ::= import | let-stmt | export .
              import ::= interface-import | component-import | func-import .
    interface-import ::= 'interface' use-path 'as' id .
    component-import ::= 'component' package-id 'as' id .
         func-import ::= 'func' id param-list result-list .
              export ::= 'export' path ('as' use-path)? .
            let-stmt ::= 'let' id '=' expression .
          expression ::= instantiation | path .
       instantiation ::= 'new' id arguments? .
           arguments ::= '{' argument (',' argument)* ','? '}' .
            argument ::= (id '=')? expression .
                path ::= id ('[' use-path ']')* .
     id-or-interface ::= id | interface .
          package-id ::= id ':' id ('@' valid-semver)? .
          param-list ::= /* from CM */
         result-list ::= /* from CM */
            use-path ::= /* from CM, e.g.: foo-bar OR foo:bar/baz@0.1.0 */ .          
           interface ::= /* from CM, e.g.: foo:bar/baz@0.1.0 */ .
                  id ::= /* from CM, e.g.: foo-bar */ .
```

Old grammar:

```ebnf
       component-def ::= 'component' id '{' component-def-items* '}' .
 component-def-items ::= import | let-stmt | export .
              import ::= id `:` interface-import | component-import .
    interface-import ::= /* from CM, i.e.: world-import-item */ .
    component-import ::= 'use' package-id 'as' id? .
              export ::= 'export' path ('as' use-path)? .
            let-stmt ::= 'let' id '=' expression .
          expression ::= instantiation | path .
       instantiation ::= 'new' id arguments? .
           arguments ::= '{' argument (',' argument)* ','? '}' .
            argument ::= (id '=')? expression .
                path ::= id ('[' use-path ']')* .
     id-or-interface ::= id | interface .
          package-id ::= id ':' id ('@' valid-semver)? .
            use-path ::= /* from CM, e.g.: foo-bar OR foo:bar/baz@0.1.0 */ .          
           interface ::= /* from CM, e.g.: foo:bar/baz@0.1.0 */ .
                  id ::= /* from CM, e.g.: foo-bar */ .
```

Random motivating scratch:
```
interface bar {
    record baz {}
    
    buz: func(b: baz)
}

interface buz {
    use bar.{baz}
}

world foo {
    import buz
}

component foo {
     import component test:foo as foo
     import interface bar as bar1
     
     import type foo = resource { bar: func() } // possible future ext.
     
     import func foo(b: baz)
     
     
     let baz = bar1[baz]
     



    // import bar: interface { ... }
    import buz: bar:baz/buz@0.1.0
    // potential alternative: import bar:baz/buz@0.1.0 as buz
    // potential alternative: let buz = import bar:baz/buz@0.1.0
    // something to indicate `buz` is a local name, not an import name

    use test:wow as wow
    
    let y = bar[buz][foo]
    
    let x = wow{buz}
}
```

```
interface bar {
    record baz {}
    
    buz: func(b: baz)
}

interface buz {
    use bar.{baz}
}

world foo {
    import buz
}

// Alternate syntax for expression the top-level component: leaving
// off the identifier to implicitly target the top-level
component {
     import component test:foo as foo
     import interface bar as bar1
     
     import type foo = resource { bar: func() } // possible future ext.
     
     import func foo(b: baz)
     
     
     let baz = bar1[baz]
     



    // import bar: interface { ... }
    import buz: bar:baz/buz@0.1.0
    // potential alternative: import bar:baz/buz@0.1.0 as buz
    // potential alternative: let buz = import bar:baz/buz@0.1.0
    // something to indicate `buz` is a local name, not an import name

    use test:wow as wow
    
    let y = bar[buz][foo]
    
    let x = wow{buz}
}

// Another possibility, using a single top-level expression to express
// a component
 let {
    import component test:foo as foo
    import interface bar as bar1
     
    import type foo = resource { bar: func() } // possible future ext.
     
    import func foo(b: baz)   
     
    baz = bar1[baz]
    
    // ...
 } in export {
   y, x
 }
```
