mirror of
https://github.com/nim-lang/Nim.git
synced 2026-09-18 11:04:53 +00:00
run runnableExamples in the module scope (#11732) [feature]
This commit is contained in:
committed by
Andreas Rumpf
parent
30f2cec671
commit
8c93c692b9
@@ -415,12 +415,6 @@ proc runAllExamples(d: PDoc) =
|
||||
rawMessage(d.conf, hintSuccess, ["runnableExamples: " & outp.string])
|
||||
removeFile(outp.changeFileExt(ExeExt))
|
||||
|
||||
proc extractImports(n: PNode; result: PNode) =
|
||||
if n.kind in {nkImportStmt, nkImportExceptStmt, nkFromStmt}:
|
||||
result.add copyTree(n)
|
||||
n.kind = nkEmpty
|
||||
return
|
||||
for i in 0..<n.safeLen: extractImports(n[i], result)
|
||||
|
||||
proc prepareExamples(d: PDoc; n: PNode) =
|
||||
var docComment = newTree(nkCommentStmt)
|
||||
@@ -430,12 +424,20 @@ proc prepareExamples(d: PDoc; n: PNode) =
|
||||
docComment,
|
||||
newTree(nkImportStmt, newStrNode(nkStrLit, d.filename)))
|
||||
runnableExamples.info = n.info
|
||||
let imports = newTree(nkStmtList)
|
||||
var savedLastSon = copyTree n.lastSon
|
||||
extractImports(savedLastSon, imports)
|
||||
for imp in imports: runnableExamples.add imp
|
||||
runnableExamples.add newTree(nkBlockStmt, newNode(nkEmpty), copyTree savedLastSon)
|
||||
for a in n.lastSon: runnableExamples.add a
|
||||
testExample(d, runnableExamples)
|
||||
when false:
|
||||
proc extractImports(n: PNode; result: PNode) =
|
||||
if n.kind in {nkImportStmt, nkImportExceptStmt, nkFromStmt}:
|
||||
result.add copyTree(n)
|
||||
n.kind = nkEmpty
|
||||
return
|
||||
for i in 0..<n.safeLen: extractImports(n[i], result)
|
||||
let imports = newTree(nkStmtList)
|
||||
var savedLastSon = copyTree n.lastSon
|
||||
extractImports(savedLastSon, imports)
|
||||
for imp in imports: runnableExamples.add imp
|
||||
runnableExamples.add newTree(nkBlockStmt, newNode(nkEmpty), copyTree savedLastSon)
|
||||
|
||||
proc getAllRunnableExamplesRec(d: PDoc; n, orig: PNode; dest: var Rope) =
|
||||
if n.info.fileIndex != orig.info.fileIndex: return
|
||||
|
||||
@@ -198,8 +198,8 @@ proc initUri*(): Uri =
|
||||
## **See also:**
|
||||
## * `Uri type <#Uri>`_ for available fields in the URI type
|
||||
runnableExamples:
|
||||
var uri: Uri
|
||||
assert initUri() == uri
|
||||
var uri2: Uri
|
||||
assert initUri() == uri2
|
||||
result = Uri(scheme: "", username: "", password: "", hostname: "", port: "",
|
||||
path: "", query: "", anchor: "")
|
||||
|
||||
|
||||
@@ -128,7 +128,7 @@ when defined(nimHasRunnableExamples):
|
||||
## a ``runnableExamples`` section is ignored.
|
||||
## - The documentation generator is aware of these examples and considers them
|
||||
## part of the ``##`` doc comment. As the last step of documentation
|
||||
## generation the examples are put into an ``$file_example.nim`` file,
|
||||
## generation each runnableExample is put in its own file ``$file_examples$i.nim``,
|
||||
## compiled and tested. The collected examples are
|
||||
## put into their own module to ensure the examples do not refer to
|
||||
## non-exported symbols.
|
||||
@@ -136,12 +136,14 @@ when defined(nimHasRunnableExamples):
|
||||
## Usage:
|
||||
##
|
||||
## .. code-block:: Nim
|
||||
## proc double(x: int): int =
|
||||
## proc double*(x: int): int =
|
||||
## ## This proc doubles a number.
|
||||
## runnableExamples:
|
||||
## ## at module scope
|
||||
## assert double(5) == 10
|
||||
## assert double(21) == 42
|
||||
##
|
||||
## block: ## at block scope
|
||||
## defer: echo "done"
|
||||
##
|
||||
## result = 2 * x
|
||||
else:
|
||||
template runnableExamples*(body: untyped) =
|
||||
|
||||
60
tests/magics/trunnableexamples.nim
Normal file
60
tests/magics/trunnableexamples.nim
Normal file
@@ -0,0 +1,60 @@
|
||||
discard """
|
||||
cmd: "nim doc $file"
|
||||
action: "compile"
|
||||
nimout: '''
|
||||
foo1
|
||||
foo2
|
||||
foo3
|
||||
foo5
|
||||
foo6
|
||||
foo7
|
||||
foo8
|
||||
foo9
|
||||
'''
|
||||
joinable: false
|
||||
"""
|
||||
|
||||
proc fun*() =
|
||||
runnableExamples:
|
||||
block: # `defer` only allowed inside a block
|
||||
defer: echo "foo1"
|
||||
|
||||
runnableExamples:
|
||||
# `fun*` only allowed at top level
|
||||
proc fun*()=echo "foo2"
|
||||
fun()
|
||||
block:
|
||||
defer: echo "foo3"
|
||||
|
||||
runnableExamples:
|
||||
# ditto
|
||||
proc fun*()=echo "foo5"
|
||||
fun()
|
||||
|
||||
runnableExamples:
|
||||
# `codeReordering` only allowed at top level
|
||||
{.experimental: "codeReordering".}
|
||||
proc fun1() = fun2()
|
||||
proc fun2() = echo "foo6"
|
||||
fun1()
|
||||
|
||||
runnableExamples:
|
||||
# only works at top level
|
||||
import std/macros
|
||||
macro myImport(a: static string): untyped =
|
||||
newTree(nnkImportStmt, [newLit a])
|
||||
myImport "str" & "utils"
|
||||
doAssert declared(isAlphaAscii)
|
||||
echo "foo7"
|
||||
|
||||
# also check for runnableExamples at module scope
|
||||
runnableExamples:
|
||||
block:
|
||||
defer: echo "foo8"
|
||||
|
||||
runnableExamples:
|
||||
proc fun*()=echo "foo9"
|
||||
fun()
|
||||
|
||||
# note: there are yet other examples where putting runnableExamples at module
|
||||
# scope is needed, for example when using an `include` before an `import`, etc.
|
||||
Reference in New Issue
Block a user