The #lang at the start of a module file begins a shorthand for a module form, much like ' is a shorthand for a quote form. Unlike ', the #lang shorthand does not work well in a REPL, in part because it must be terminated by an end-of-file, but also because the longhand expansion of #lang depends on the name of the enclosing file.
6.2.1 The module Form
The longhand form of a module declaration, which works in a REPL as well as a file, is
(module name-id initial-module-path decl ...)
where the name-id is a name for the module, initial-module-path is an initial import, and each decl is an import, export, definition, or expression. In the case of a file, name-id normally matches the name of the containing file, minus its directory path or file extension, but name-id is ignored when the module is required through its file’s path.
The initial-module-path is needed because even the require form must be imported for further use in the module body. In other words, the initial-module-path import bootstraps the syntax that is available in the body. The most commonly used initial-module-path is racket, which supplies most of the bindings described in this guide, including require, define, and provide. Another commonly used initial-module-path is racket/base, which provides less functionality, but still much of the most commonly needed functions and syntax.
For example, the "cake.rkt" example of the previous section could be written as
(module cake racket (provide print-cake) (define (print-cake n) (show " ~a " n #\.) (show " .-~a-. " n #\|) (show " | ~a | " n #\space) (show "---~a---" n #\-)) (define (show fmt n ch) (printf fmt (make-string n ch)) (newline)))
Declaring a module does not immediately evaluate the body definitions and expressions of the module. The module must be explicitly required at the top level to trigger evaluation. After evaluation is triggered once, later requires do not re-evaluate the module body.
The body of a #lang shorthand has no specific syntax, because the syntax is determined by the language name that follows #lang.
In the case of #lang racket, the syntax is
which reads the same as
where name is derived from the name of the file that contains the #lang form.
The #lang racket/base form has the same syntax as #lang racket, except that the longhand expansion uses racket/base instead of racket. The #lang scribble/manual form, in contrast, has a completely different syntax that doesn’t even look like Racket, and which we do not attempt to describe in this guide.
Unless otherwise specified, a module that is documented as a “language” using the #lang notation will expand to module in the same way as #lang racket. The documented language name can be used directly with module or require, too.
A module form can be nested within a module, in which case the nested module form declares a submodule. Submodules can be referenced directly by the enclosing module using a quoted name. The following example prints "Tony" by importing tiger from the zoo submodule:
Running a module does not necessarily run its submodules. In the above example, running "park.rkt" runs its submodule zoo only because the "park.rkt" module requires the zoo submodule. Otherwise, a module and each of its submodules can be run independently. Furthermore, if "park.rkt" is compiled to a bytecode file (via raco make), then the code for "park.rkt" or the code for zoo can be loaded independently.
Submodules can be nested within submodules, and a submodule can be referenced directly by a module other than its enclosing module by using a submodule path.
(module* name-id initial-module-path-or-#f decl ...)
In addition, a module* form can specify #f in place of an
initial-module-path, in which case the submodule sees all of
the enclosing module’s bindings—
One use of submodules declared with module* and #f is to export additional bindings through a submodule that are not normally exported from the module:
In this revised "cake.rkt" module, show is not imported by a module that uses (require "cake.rkt"), since most clients of "cake.rkt" will not want the extra function. A module can require the extra submodule using (require (submod "cake.rkt" extras)) to access the otherwise hidden show function.See submodule paths for more information on submod.
The following variant of "cake.rkt" includes a main submodule that calls print-cake:
Running a module does not run its module*-defined submodules. Nevertheless, running the above module via racket or DrRacket prints a cake with 10 candles, because the main submodule is a special case.
When a module is provided as a program name to the racket executable or run directly within DrRacket, if the module has a main submodule, the main submodule is run after its enclosing module. Declaring a main submodule thus specifies extra actions to be performed when a module is run directly, instead of required as a library within a larger program.
A main submodule does not have to be declared with module*. If the main module does not need to use bindings from its enclosing module, it can be declared with module. More commonly, main is declared using module+:
(module+ name-id decl ...)
A submodule declared with module+ is like one declared with module* using #f as its initial-module-path. In addition, multiple module+ forms can specify the same submodule name, in which case the bodies of the module+ forms are combined to create a single submodule.
The combining behavior of module+ is particularly useful for defining a test submodule, which can be conveniently run using raco test in much the same way that main is conveniently run with racket. For example, the following "physics.rkt" module exports drop and to-energy functions, and it defines a test module to hold unit tests:
#lang racket (module+ test (require rackunit) (define ε 1e-10)) (provide drop to-energy) (define (drop t) (* 1/2 9.8 t t)) (module+ test (check-= (drop 0) 0 ε) (check-= (drop 10) 490 ε)) (define (to-energy m) (* m (expt 299792458.0 2))) (module+ test (check-= (to-energy 0) 0 ε) (check-= (to-energy 1) 9e+16 1e+15))
Importing "physics.rkt" into a larger program does not run
the drop and to-energy tests—
The above "physics.rkt" module is equivalent to using module*: