diff --git a/src/PkgTemplates.jl b/src/PkgTemplates.jl index d6769d0e..d8a0312d 100644 --- a/src/PkgTemplates.jl +++ b/src/PkgTemplates.jl @@ -40,4 +40,15 @@ include("generate.jl") include("plugin.jl") include("interactive.jl") +# Run some function with a project activated at the given path. +function with_project(f::Function, path::AbstractString) + proj = current_project() + try + Pkg.activate(path) + f() + finally + proj === nothing ? Pkg.activate() : Pkg.activate(proj) + end +end + end diff --git a/src/generate.jl b/src/generate.jl index 7a1716d5..0c240e81 100644 --- a/src/generate.jl +++ b/src/generate.jl @@ -57,6 +57,13 @@ function (t::Template)(pkg::AbstractString) Pkg.develop(PackageSpec(; path=pkg_dir)) end + manifest = joinpath(pkg_dir, "Manifest.toml") + if t.manifest && !isfile(manifest) + # If the manifest is going to be committed, make sure it's generated. + touch(manifest) + with_project(Pkg.update, pkg_dir) + end + @info "New package is at $pkg_dir" catch rm(pkg_dir; recursive=true, force=true) diff --git a/src/plugins/defaults.jl b/src/plugins/defaults.jl index fdc14191..e69ecf9c 100644 --- a/src/plugins/defaults.jl +++ b/src/plugins/defaults.jl @@ -1,4 +1,5 @@ const TEST_UUID = "8dfed614-e22c-5e08-85e1-65c5234f0b40" +const TEST_DEP = PackageSpec(; name="Test", uuid=TEST_UUID) const LICENSE_DIR = normpath(joinpath(@__DIR__, "..", "..", "licenses")) const LICENSES = Dict( "MIT" => "MIT \"Expat\" License", @@ -143,15 +144,21 @@ function gen_plugin(p::Gitignore, t::Template, pkg_dir::AbstractString) end """ - Tests(; file="$(contractuser(default_file("runtests.jl")))" -> Tests + Tests(; file="$(contractuser(default_file("runtests.jl")))", project=false) Sets up testing for packages. ## Keyword Arguments - `file::AbstractString`: Template file for the `runtests.jl`. +- `project::Bool`: Whether or not to create a new project for tests (`test/Project.toml`). + See [here](https://julialang.github.io/Pkg.jl/v1/creating-packages/#Test-specific-dependencies-in-Julia-1.2-and-above-1) for more details. + +!!! note + Managing test dependencies with `test/Project.toml` is only supported in Julia 1.2 and later. """ @with_kw_noshow struct Tests <: BasicPlugin file::String = default_file("runtests.jl") + project::Bool = false end source(p::Tests) = p.file @@ -162,21 +169,27 @@ function gen_plugin(p::Tests, t::Template, pkg_dir::AbstractString) # Do the normal BasicPlugin behaviour to create the test script. invoke(gen_plugin, Tuple{BasicPlugin, Template, AbstractString}, p, t, pkg_dir) - # Add Test as a test-only dependency. + # Then set up the test depdendency in the chosen way. + f = p.project ? make_test_project : add_test_dependency + f(pkg_dir) +end + +# Create a new test project. +function make_test_project(pkg_dir::AbstractString) + with_project(() -> Pkg.add(TEST_DEP), joinpath(pkg_dir, "test")) +end + +# Add Test as a test-only dependency. +function add_test_dependency(pkg_dir::AbstractString) + # Add the dependency manually since there's no programmatic way to add to [extras]. path = joinpath(pkg_dir, "Project.toml") toml = TOML.parsefile(path) get!(toml, "extras", Dict())["Test"] = TEST_UUID get!(toml, "targets", Dict())["test"] = ["Test"] open(io -> TOML.print(io, toml), path, "w") - # Generate the manifest. + # Generate the manifest by updating the project. # This also ensures that keys in Project.toml are sorted properly. touch(joinpath(pkg_dir, "Manifest.toml")) # File must exist to be modified by Pkg. - proj = current_project() - try - Pkg.activate(pkg_dir) - Pkg.update() - finally - proj === nothing ? Pkg.activate() : Pkg.activate(proj) - end + with_project(Pkg.update, pkg_dir) end diff --git a/src/plugins/documenter.jl b/src/plugins/documenter.jl index dc61dd01..3ff2ac18 100644 --- a/src/plugins/documenter.jl +++ b/src/plugins/documenter.jl @@ -1,4 +1,7 @@ -const DOCUMENTER_UUID = "e30172f5-a6a5-5a46-863b-614d45cd2de4" +const DOCUMENTER_DEP = PackageSpec(; + name="Documenter", + uuid="e30172f5-a6a5-5a46-863b-614d45cd2de4", +) """ Documenter{T<:Union{TravisCI, GitLabCI, Nothing}}(; @@ -98,13 +101,7 @@ function gen_plugin(p::Documenter, t::Template, pkg_dir::AbstractString) foreach(a -> cp(a, joinpath(assets_dir, basename(a))), p.assets) # Create the documentation project. - proj = current_project() - try - Pkg.activate(docs_dir) - Pkg.add(PackageSpec(; name="Documenter", uuid=DOCUMENTER_UUID)) - finally - proj === nothing ? Pkg.activate() : Pkg.activate(proj) - end + with_project(() -> Pkg.add(DOCUMENTER_DEP), docs_dir) end github_pages_url(t::Template, pkg::AbstractString) = "https://$(t.user).github.io/$pkg.jl" diff --git a/src/template.jl b/src/template.jl index 8ef31542..da175bf2 100644 --- a/src/template.jl +++ b/src/template.jl @@ -89,13 +89,21 @@ function Template(::Val{false}; kwargs...) # which means that default plugins get replaced by user values. plugins = Dict(typeof(p) => p for p in enabled) + # TODO: It might be nice to offer some kind of warn_incompatible function + # to be optionally implented by plugins instead of hardcoding this case here. + julia = getkw(kwargs, :julia_version) + julia < v"1.2" && haskey(plugins, Tests) && plugins[Tests].project && @warn string( + "The Tests plugin is set to create a project (supported in Julia 1.2 and later)", + "but a Julia version older than 1.2 is supported.", + ) + return Template( authors, getkw(kwargs, :develop), dir, getkw(kwargs, :git), host, - getkw(kwargs, :julia_version), + julia, getkw(kwargs, :manifest), plugins, getkw(kwargs, :ssh), diff --git a/test/fixtures/AllPlugins/README.md.txt b/test/fixtures/AllPlugins/README.md.txt index 35d94a0f..44735f9f 100644 --- a/test/fixtures/AllPlugins/README.md.txt +++ b/test/fixtures/AllPlugins/README.md.txt @@ -7,7 +7,3 @@ [![Build Status](https://api.cirrus-ci.com/github/tester/.jl.svg)](https://cirrus-ci.com/github/tester/AllPlugins.jl) [![Coverage](https://codecov.io/gh//.jl/branch/master/graph/badge.svg)](https://codecov.io/gh//.jl) [![Coverage](https://coveralls.io/repos/github//.jl/badge.svg?branch=master)](https://coveralls.io/github//.jl?branch=master) - -## Citing - -See [`CITATION.bib`](CITATION.bib) for the relevant reference(s). diff --git a/test/show.jl b/test/show.jl index b51aba8f..b48fe7ff 100644 --- a/test/show.jl +++ b/test/show.jl @@ -37,6 +37,7 @@ const LICENSE_DIR = contractuser(PT.LICENSE_DIR) inline_badges: false Tests: file: "$DEFAULTS_DIR/runtests.jl" + project: false """ @test sprint(show, MIME("text/plain"), tpl(; authors=USER)) == rstrip(expected) end