Class: Abqari::CLI::New

Inherits:
Object
  • Object
show all
Defined in:
lib/abqari/cli/new.rb

Overview

abqari new <projectname> — scaffolds a new Abqari site by recursive-copying lib/abqari/templates/site_skeleton/ into the target directory, with simple ERB token substitution on files whose name ends in .tt. Modelled on Jekyll's jekyll new, Rails's rails new, and Astro's npm create astro@latest.

Defaults — zero prompts:

* `title:`       = the projectname, title-cased
* `description:` = a short placeholder
* `author:`      = "Your name" (operator edits later)
* `theme:`       = minimal
* `locale:`      = en
* Engine source  = whichever shape the user passes via
                 `--engine`. Defaults to "rubygems" (the
                 published gem, pinned to the current
                 major.minor).

Flags:

--name "..."          Site title (defaults to projectname)
--description "..."   Site description
--author "..."        Author
--theme NAME          Theme (one of VALID_THEMES below)
--locale CODE         ISO 639-1 (en, fr, ja, …)
--with LIST           Extra collections to enable alongside posts
                    (comma-separated: photos, publications,
                    workshops — repeatable). For each one the
                    scaffold sets `enabled: true` in
                    config/site.yml AND creates the
                    `content/<name>/index.md` collection index
                    page (a real content file the engine does
                    not auto-generate). Everything stays
                    opt-in-able later by hand; the flag just
                    removes the copy-an-example friction.
--engine SOURCE       'rubygems' (default — the published gem),
                    'git' (github URL placeholder — operator
                    edits to point at their fork), or 'path'
                    (path-source to ../abqari, useful for
                    engine devs).
--blank               Bare-minimum scaffold: no example post,
                    no tutorial text on the home / about
                    pages, no in-line docs in
                    `config/site.yml`. Useful for users who
                    already know Abqari and want a clean
                    slate. Default mode includes a welcome
                    post, populated home page, and heavily-
                    commented config to demo the surface.
--skip-bundle         Skip running `bundle install` afterwards
--force               Overwrite target directory if non-empty

Constant Summary collapse

VALID_THEMES =
%w[minimal magazine notebook sand bootstrap custom none].freeze
VALID_ENGINES =
%w[rubygems git path].freeze
WITH_COLLECTIONS =

Collections --with can enable. Posts is always on — it's the backbone collection (disable it in config/site.yml if you must).

%w[photos publications workshops].freeze
COLLECTION_CONTENT_PATHS =

Skeleton paths that only copy when their collection is selected via --with. Each matches itself and anything underneath it.

{
  'photos'       => 'content/photos',
  'publications' => 'content/publications',
  'workshops'    => 'content/workshops'
}.freeze
BLANK_MODE_SKIP =

Directories that are example-only — skipped when --blank is passed. Paths are relative to the skeleton root, no trailing slash. Each path matches itself AND anything underneath it.

%w[
  content/posts/welcome
].freeze
DEFAULT_RUBYGEMS_GEMFILE_LINE =

Engine-source line in the scaffolded Gemfile, one per --engine option. The default pins to the running engine's major.minor so a scaffolded site tracks patch releases but not breaking ones. The git line defaults to the canonical repo so it bundles out of the box — operators tracking a fork edit the URL.

"gem 'abqari', '~> #{Abqari::VERSION.split('.').first(2).join('.')}'"
THEMING_DOC_URL =

Docs referenced from generated files must be FULL URLs. A scaffolded site has no docs/ directory — that lives in the engine repo and isn't shipped in the gem — so a bare docs/theming.md in a site's own config sent the reader looking for a file they'll never find.

'https://github.com/grantrayner/abqari/blob/main/docs/theming.md'
DEFAULT_GIT_GEMFILE_LINE =
"gem 'abqari', git: 'https://github.com/grantrayner/abqari.git'"
DEFAULT_PATH_GEMFILE_LINE =
"gem 'abqari', path: '../abqari'"

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initializeNew

Returns a new instance of New.



100
101
102
103
104
105
106
107
108
109
110
# File 'lib/abqari/cli/new.rb', line 100

def initialize
  @options = {
    theme:         'minimal',
    locale:        'en',
    engine:        'rubygems',
    with:          [],
    blank:         false,
    skip_bundle:   false,
    force:         false
  }
end

Class Method Details

.run(argv) ⇒ Object



96
97
98
# File 'lib/abqari/cli/new.rb', line 96

def self.run(argv)
  new.run(argv)
end

Instance Method Details

#run(argv) ⇒ Object



112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
# File 'lib/abqari/cli/new.rb', line 112

def run(argv)
  parser = build_parser
  rest = parser.parse(argv)

  if rest.empty?
    warn parser.help
    warn "\nMissing required argument: projectname"
    return false
  end

  if rest.length > 1
    warn "Ignoring extra argument(s): #{rest[1..].map(&:inspect).join(', ')}"
    warn 'Quote the name if it contains spaces: abqari new "my blog site"'
    warn ''
  end

  projectname = rest.first
  return false unless valid_projectname?(projectname)

  target_dir  = File.expand_path(projectname)

  return false unless preflight_ok?(target_dir)
  return false unless validate_options!

  copy_skeleton!(target_dir, build_template_vars(projectname))
  materialize_theme!(target_dir)
  bundled = @options[:skip_bundle] ? true : run_bundle_install!(target_dir)

  # Next steps print either way — the site exists and the reader
  # needs to know where it is — but the exit status reflects
  # whether it's actually ready to build.
  print_next_steps(projectname, target_dir)
  bundled
end