squared 0.4.16 → 0.4.17

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 42a856b40866dc4f90ff4def50a0d8ef6f7134ce5cd8f0c40064b55aea2735a4
4
- data.tar.gz: 1ee4f68f6f3a40ed0d45fac5fbb7e3817787f9c86be7770331edbaff541e7ad1
3
+ metadata.gz: 4e41d76a0edb3135560234d2a7faf8eba688365316cad1dc9ca38d7fb353759d
4
+ data.tar.gz: b59fa903ae6e7282ef8d3b36039141c9b29f43c0f7d5fdc64063cd191e7cb409
5
5
  SHA512:
6
- metadata.gz: ffb1e276cc3fa97d5de20158a5d0833c8cd140506cc8ee2fd61e0c19fe446e12edba1dca5cc0cda49a4e5d0e393bae4db1fa8f5320aa8bfb892c1dd8608d31ae
7
- data.tar.gz: e6460b7953fd893b7560a051d93e86630faf134d831e173d25924562775186a6f46dd0a9cb13014a4adc8c2ff3ed734719925653ccd9ef140e4fa572e36db15c
6
+ metadata.gz: 7118f35ce60a5a8008c3163b636b7acbcbfeb637b2cea7aab9fb3be87b5a4701d0f28c8edbe2510a9e596077f578875bea537acebedc4177223a63d377ea418f
7
+ data.tar.gz: '025669293a2bf52bed8c2a25135264faa04363e646f2bd217a1a26e89fddaa4cab84cafedd4c31ba82045c1471d4c82da39e4c15fd353201bcc2b789bcbb0c1d'
data/CHANGELOG.md CHANGED
@@ -1,5 +1,35 @@
1
1
  # Changelog
2
2
 
3
+ ## [0.4.17] - 2025-08-09
4
+
5
+ ### Added
6
+
7
+ - Node repos can be initialized with specific package manager.
8
+ - Docker Engine options were updated to 28.0.
9
+ - Git commands pull and fetch action all was implemented.
10
+ - Git command reset action undo was implemented.
11
+ - Python command pip action upgrade was implemented.
12
+ - Git commands refs and files can use both pathspec and pattern.
13
+ - Git command submodule was implemented.
14
+ - Git command status was implemented.
15
+ - Git command switch action branch was implemented.
16
+
17
+ ### Changed
18
+
19
+ - Project task events can be assigned to a single proc.
20
+ - Ruby task copy uses require paths from gem specification.
21
+ - Docker task build:bake was renamed bake:build.
22
+ - Project global tasks can be hidden and still expose subtasks.
23
+ - Repo command line options can be overriden with class method.
24
+ - Repo task all variable REPO_DRYRUN was replaced with REPO_STAGE.
25
+ - Repo command sync option no-fail was renamed fail.
26
+
27
+ ### Fixed
28
+
29
+ - Gem command outdated did not work outside main project folder.
30
+ - Node command bump did not reset major and minor trailing digits.
31
+ - Docker image status message was displayed backwards.
32
+
3
33
  ## [0.4.16] - 2025-07-27
4
34
 
5
35
  ### Added
@@ -861,6 +891,7 @@
861
891
 
862
892
  - Changelog was created.
863
893
 
894
+ [0.4.17]: https://github.com/anpham6/squared/releases/tag/v0.4.17-ruby
864
895
  [0.4.16]: https://github.com/anpham6/squared/releases/tag/v0.4.16-ruby
865
896
  [0.4.15]: https://github.com/anpham6/squared/releases/tag/v0.4.15-ruby
866
897
  [0.4.14]: https://github.com/anpham6/squared/releases/tag/v0.4.14-ruby
data/README.md CHANGED
@@ -1,4 +1,4 @@
1
- # squared 5.5
1
+ # squared 5.6
2
2
 
3
3
  ## Documentation
4
4
 
@@ -140,13 +140,13 @@ rake clone # node + docs
140
140
  # PIPE_FAIL={0,1}
141
141
  # PORT=3000
142
142
  docker build -t squared --build-arg MANIFEST=prod --build-arg NODE_ENV=production .
143
- docker build -t node --build-arg NODE_TAG=22 --build-arg NODE_INSTALL=pnpm -f slim.Dockerfile .
143
+ docker build -t node --build-arg NODE_TAG=22 --build-arg NODE_INSTALL=pnpm -f Dockerfile.slim .
144
144
  NODE=22 docker buildx bake node
145
145
  # OR
146
- docker build -t ruby --build-arg RUBY_TAG=3.4.0 --build-arg NODE_VERSION=22 --build-arg PIPE_FAIL=0 -f ruby.Dockerfile .
146
+ docker build -t ruby --build-arg RUBY_TAG=3.4.0 --build-arg NODE_VERSION=22 --build-arg PIPE_FAIL=0 -f Dockerfile.ruby .
147
147
  RUBY=3.4.0 docker buildx bake ruby
148
148
  # OR
149
- docker build -t nginx --build-arg NGINX_VERSION=1.27 --build-arg PORT=3000 --build-arg NODE_VERSION=20 -f nginx.Dockerfile .
149
+ docker build -t nginx --build-arg NGINX_VERSION=1.27 --build-arg PORT=3000 --build-arg NODE_VERSION=20 -f Dockerfile.nginx .
150
150
  NGINX=1.27 docker buildx bake nginx
151
151
 
152
152
  # Express
@@ -175,6 +175,9 @@ docker run -it --name debian squared /bin/bash # irb
175
175
  > * https://unpkg.com/squared/dist/squared.min.js
176
176
  > * https://unpkg.com/squared/dist/vdom-lite.framework.min.js
177
177
 
178
+ > [!WARNING]
179
+ > Safari is completely untested and is not an officially supported browser.
180
+
178
181
  ## Usage
179
182
 
180
183
  Library files are in the `/dist` folder. A minimum of **two** files are required to run *squared*.
@@ -378,7 +381,7 @@ Used primarly for developing single page layouts but can also bundle assets usin
378
381
 
379
382
  ### Example: vdom
380
383
 
381
- The most minimal framework possible (*55kb gzipped*) and can be useful when debugging through DevTools. The `lite` version is about half the bundle size and is recommended for most browser applications.
384
+ The most minimal framework possible (*80kb gzipped*) and can be useful when debugging through DevTools. The `lite` version is about half the bundle size and is recommended for most browser applications.
382
385
 
383
386
  * ES2018
384
387
 
@@ -416,6 +419,7 @@ squared.settings = {
416
419
  targetAPI: 35,
417
420
  supportRTL: true,
418
421
  supportNegativeLeftTop: true,
422
+ supportUnicode: ["emoji"], // true | "utf-16" | "emoji"
419
423
  preloadImages: true,
420
424
  preloadFonts: true,
421
425
  preloadLocalFonts: true, // Chromium
@@ -464,6 +468,7 @@ squared.settings = {
464
468
  outputMainFileName: "activity_main.xml",
465
469
  outputFragmentFileName: "fragment_main.xml",
466
470
  /* Project - parseDocument (first only) */
471
+ supportUnicode: "utf-16",
467
472
  resourceQualifier: "", // "land" -> "res/layout-land" | "port" -> "res/layout-port" (appended to every "res" folder)
468
473
  resourceSystemColors: {
469
474
  "system_accent1_100": "white", // Will be converted to ARGB
data/README.ruby.md CHANGED
@@ -88,7 +88,7 @@ Workspace::Application
88
88
  .add("e-mc", "emc", copy: { from: "publish", scope: "@e-mc", also: [:pir, "squared-express/"] }, ref: :node) # Node
89
89
  .add("pi-r", "pir", copy: { from: "publish", scope: "@pi-r" }, clean: ["publish/**/*.js", "tmp/"]) # Trailing slash required for directories
90
90
  .add("pi-r2", "pir2", copy: { from: :npm, also: %i[squared express], files: ["LICENSE", ["README.md.ruby", "README.md"]] }) # Uses dist files from NPM package spec
91
- .add("squared", script: ["build:stage1", "build:stage2"], group: "app") do # Copy target (main)
91
+ .add("squared", init: 'pnpm', script: ["build:stage1", "build:stage2"], group: "app") do # Use pnpm/yarn/berry for depend + Copy target (main)
92
92
  # Repo (global)
93
93
  as(:run, "build:dev", "dev") # npm run build:dev -> npm run dev
94
94
  as(:run, { "build:dev": "dev", "build:prod": "prod" })
@@ -499,11 +499,11 @@ Most project classes will inherit from `Git` which enables these tasks:
499
499
  | checkout | checkout | commit branch track detach path |
500
500
  | commit | commit | add all amend amend-orig fixup |
501
501
  | diff | diff | head cached branch files between contain |
502
- | fetch | fetch | origin remote |
502
+ | fetch | fetch | origin remote all |
503
503
  | files | ls-files | cached modified deleted others |
504
- | git | | add clean mv rm revert |
504
+ | git | | add blame clean mv rm revert |
505
505
  | merge | merge | commit no-commit send |
506
- | pull | pull | origin remote |
506
+ | pull | pull | origin remote all |
507
507
  | rebase | rebase | branch onto send |
508
508
  | refs | ls-remote --refs | heads tags remote |
509
509
  | reset | reset | commit index patch mode |
@@ -511,7 +511,7 @@ Most project classes will inherit from `Git` which enables these tasks:
511
511
  | rev | rev | commit output |
512
512
  | show | show | format oneline |
513
513
  | stash | stash | push pop apply branch drop clear list |
514
- | switch | switch | create detach merge |
514
+ | switch | switch | branch create detach |
515
515
  | tag | tag | add sign delete list |
516
516
 
517
517
  You can disable all of them at once using the `exclude` property.
@@ -625,6 +625,8 @@ LOG_LEVEL # See gem "logger"
625
625
 
626
626
  ### Git
627
627
 
628
+ * Version: 2.50
629
+
628
630
  ```sh
629
631
  GIT_OPTIONS=q,strategy=ort # all
630
632
  GIT_OPTIONS_${NAME}=v,ff # project only
@@ -634,15 +636,15 @@ GIT_AUTOSTASH_${NAME}=0 # rebase (project only)
634
636
 
635
637
  | Command | Flag | ENV |
636
638
  | :--------- | :---------------- | :-------------------------------------------------------------------- |
637
- | branch | create | TRACK=0,1,s FORCE |
638
- | branch | move copy | FORCE |
639
+ | branch | create | TRACK=0,1,s F|FORCE |
640
+ | branch | move copy | F|FORCE |
639
641
  | branch | set delete | COUNT=n |
640
642
  | branch | global | SYNC |
641
643
  | checkout | branch | DETACH TRACK=s COUNT=n |
642
644
  | checkout | detach | REFLOG=1 |
643
645
  | checkout | track | COUNT=n |
644
646
  | checkout | global path | HEAD=s PATHSPEC=s |
645
- | checkout | * | FORCE MERGE |
647
+ | checkout | * | F|FORCE MERGE |
646
648
  | clone | * | DEPTH=n ORIGIN=s BRANCH=s REVISION=s LOCAL=0,1 |
647
649
  | commit | * | UPSTREAM=s DRY_RUN EDIT=0 M|MESSAGE=s |
648
650
  | diff | -between -contain | MERGE_BASE |
@@ -650,13 +652,13 @@ GIT_AUTOSTASH_${NAME}=0 # rebase (project only)
650
652
  | diff | * | PATHSPEC=s |
651
653
  | fetch | -remote | ALL |
652
654
  | fetch | remote | REFSPEC=s |
653
- | fetch | * | FORCE RECURSE_SUBMODULES=0,1,s |
655
+ | fetch | * | F|FORCE RECURSE_SUBMODULES=0,1,s |
654
656
  | git | rm | PATHSPEC=s |
655
657
  | log | * | PATHSPEC=s |
656
658
  | pull | rebase | AUTOSTASH |
657
659
  | pull | remote | REFSPEC=s |
658
660
  | pull | -remote | ALL |
659
- | pull | * | REBASE=0,1 FORCE RECURSE_SUBMODULES=0,1,s |
661
+ | pull | * | REBASE=0,1 F|FORCE RECURSE_SUBMODULES=0,1,s |
660
662
  | rebase | branch | HEAD=s |
661
663
  | rebase | onto | INTERACTIVE I HEAD=s |
662
664
  | reset | mode (mixed) | N REFRESH=0 |
@@ -670,14 +672,16 @@ GIT_AUTOSTASH_${NAME}=0 # rebase (project only)
670
672
  | status | global | BRANCH LONG IGNORE_SUBMODULES=s,0-3 PATHSPEC=s |
671
673
  | switch | detach | REFLOG=1 |
672
674
  | switch | -detach | HEAD=s |
673
- | switch | * | FORCE |
675
+ | switch | * | F|FORCE |
674
676
  | tag | add | SIGN FORCE HEAD=s M|MESSAGE=s |
675
- | tag | sign | FORCE HEAD=s M|MESSAGE=s |
677
+ | tag | sign | F|FORCE HEAD=s M|MESSAGE=s |
676
678
  | tag | delete | COUNT=n |
677
679
  | rev | commit branch | HEAD=s |
678
680
 
679
681
  ### Docker
680
682
 
683
+ * Version: 28.3
684
+
681
685
  ```sh
682
686
  DOCKER_OPTIONS=q,no-cache # all
683
687
  DOCKER_OPTIONS_${NAME}=v,no-cache=false # project only (override)
@@ -712,7 +716,7 @@ REPO_WARN # 0,1
712
716
  REPO_SYNC # 0,1
713
717
  REPO_URL # manifest repository
714
718
  REPO_MANIFEST # e.g. latest,nightly,prod
715
- REPO_DRYRUN # 0,1,2
719
+ REPO_STAGE # 0,1,2,3
716
720
  REPO_TIMEOUT # confirm dialog (seconds)
717
721
  ```
718
722
 
@@ -12,9 +12,9 @@ module Squared
12
12
  if RUBY_ENGINE == 'jruby' && Rake::Win32.windows?
13
13
  e = kwargs[:exception]
14
14
  if (dir = kwargs[:chdir]) && ((pwd = Dir.pwd) != dir)
15
- Dir.chdir(dir)
15
+ Dir.chdir dir
16
16
  ret = Kernel.send(name, *args)
17
- Dir.chdir(pwd)
17
+ Dir.chdir pwd
18
18
  else
19
19
  ret = Kernel.send(name, *args)
20
20
  end
@@ -57,23 +57,24 @@ module Squared
57
57
  soft = 0
58
58
  subdir.each do |dir, files|
59
59
  if link
60
- items = files.dup
61
- files.clear
62
- items.each do |file|
63
- if file.exist?
64
- if file.symlink?
65
- next unless force
60
+ files.dup.tap do |items|
61
+ files.clear
62
+ items.each do |file|
63
+ if file.exist?
64
+ if file.symlink?
65
+ next unless force
66
+ else
67
+ files << file
68
+ next
69
+ end
70
+ end
71
+ if link == 'hard'
72
+ FileUtils.ln(file, dir, force: force, verbose: false)
66
73
  else
67
- files << file
68
- next
74
+ FileUtils.ln_s(file, dir, force: force, verbose: false)
69
75
  end
76
+ soft += 1
70
77
  end
71
- if link == 'hard'
72
- FileUtils.ln(file, dir, force: force, verbose: false)
73
- else
74
- FileUtils.ln_s(file, dir, force: force, verbose: false)
75
- end
76
- soft += 1
77
78
  end
78
79
  end
79
80
  next if files.empty?
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Squared
4
- VERSION = '0.4.16'
4
+ VERSION = '0.4.17'
5
5
  end
@@ -26,7 +26,7 @@ module Squared
26
26
  next unless base || obj < impl_project
27
27
 
28
28
  if base
29
- @impl_project = obj
29
+ self.impl_project = obj
30
30
  impl_series.base_set(obj)
31
31
  else
32
32
  kind_project.unshift(obj)
@@ -39,7 +39,7 @@ module Squared
39
39
  impl_series.alias(*args)
40
40
  end
41
41
  if (args = obj.bannerargs)
42
- @attr_banner.merge(args)
42
+ attr_banner.merge(args)
43
43
  end
44
44
  end
45
45
  end
@@ -691,9 +691,14 @@ module Squared
691
691
  private
692
692
 
693
693
  def __build__(default: nil, **)
694
- return unless default && task_defined?(out = task_name(default))
695
-
696
- task Rake.application.default_task_name => out
694
+ unless task_defined?('squared:version')
695
+ task 'squared:version' do
696
+ puts Squared::VERSION
697
+ end
698
+ end
699
+ if default && task_defined?(out = task_name(default))
700
+ task Rake.application.default_task_name => out
701
+ end
697
702
  end
698
703
 
699
704
  def __chain__(*)
@@ -21,8 +21,8 @@ module Squared
21
21
  VAR_SET = %i[parent global script index envname desc dependfile dependindex theme archive env dev prod graph
22
22
  pass only exclude].freeze
23
23
  BLK_SET = %i[run depend doc lint test copy clean].freeze
24
- SEM_VER = /\b(\d+)(?:(\.)(\d+))?(?:(\.)(\d+)(\S+)?)?\b/.freeze
25
- URI_SCHEME = %r{^([a-z][a-z\d+-.]*)://[^@:\[\]\\^<>|\s]}i.freeze
24
+ SEM_VER = /\b(\d+)(?:(\.)(\d+))?(?:(\.)(\d+))?-?(\S+)?\b/.freeze
25
+ URI_SCHEME = %r{\A([a-z][a-z\d+-.]*)://[^@:\[\]\\^<>|\s]}i.freeze
26
26
  TASK_METADATA = Rake::TaskManager.record_task_metadata
27
27
  private_constant :VAR_SET, :BLK_SET, :SEM_VER, :URI_SCHEME, :TASK_METADATA
28
28
 
@@ -208,7 +208,7 @@ module Squared
208
208
  def initialize_env(dev: nil, prod: nil, **)
209
209
  @dev = env_match('BUILD', dev, suffix: 'DEV', strict: true)
210
210
  @prod = env_match('BUILD', prod, suffix: 'PROD', strict: true)
211
- if @output[2] != false && (val = env('BUILD', suffix: 'ENV'))
211
+ unless @output[2] == false || !(val = env('BUILD', suffix: 'ENV'))
212
212
  @output[2] = parse_json(val, hint: "BUILD_#{@envname}_ENV") || @output[2]
213
213
  end
214
214
  unless @output[0] == false || @output[0].is_a?(Array)
@@ -662,7 +662,7 @@ module Squared
662
662
  when 128, 'sha512'
663
663
  Digest::SHA512
664
664
  else
665
- raise_error("invalid checksum: #{digest}", hint: name)
665
+ raise_error "invalid checksum: #{digest}"
666
666
  end
667
667
  end
668
668
  if (val = env('HEADERS')) && (val = parse_json(val, hint: "HEADERS_#{@envname}"))
@@ -994,7 +994,7 @@ module Squared
994
994
  end
995
995
 
996
996
  def run(cmd = @session, var = nil, exception: self.exception, sync: true, from: nil, banner: true, chdir: path,
997
- interactive: nil, **)
997
+ interactive: nil, hint: nil, **)
998
998
  unless cmd
999
999
  warn log_message(Logger::WARN, 'no command given', subject: project, hint: from || 'unknown', pass: true)
1000
1000
  return
@@ -1022,7 +1022,7 @@ module Squared
1022
1022
  log&.warn "ENV discarded: #{var}" if var
1023
1023
  task_invoke(cmd, exception: exception, warning: warning?)
1024
1024
  else
1025
- print_item format_banner(cmd, banner: banner) if sync
1025
+ print_item format_banner(hint ? "#{cmd} (#{hint})" : cmd, banner: banner) if sync
1026
1026
  if var != false && (pre = runenv)
1027
1027
  case pre
1028
1028
  when Hash
@@ -1261,7 +1261,7 @@ module Squared
1261
1261
  def session_done(cmd)
1262
1262
  return cmd unless cmd.respond_to?(:done)
1263
1263
 
1264
- raise_error('no args added', hint: cmd.first || name) unless cmd.size > 1
1264
+ raise_error('no args added', hint: cmd.first) unless cmd.size > 1
1265
1265
  @session = nil if cmd == @session
1266
1266
  cmd.done
1267
1267
  end
@@ -1420,7 +1420,7 @@ module Squared
1420
1420
  unless items.empty?
1421
1421
  pad = items.size.to_s.size
1422
1422
  items.each_with_index do |val, i|
1423
- next unless reg.empty? || reg.any? { |pat| val[0].match?(pat) }
1423
+ next unless matchany?(val[0], reg)
1424
1424
 
1425
1425
  out << "#{i.succ.to_s.rjust(pad)}. #{each ? each.call(val) : val[0]}"
1426
1426
  end
@@ -1744,6 +1744,17 @@ module Squared
1744
1744
  files.map { |val| val == '.' ? '.' : shell_quote(path + val) }
1745
1745
  end
1746
1746
 
1747
+ def matchmap(list, prefix = nil)
1748
+ list.map do |val|
1749
+ if val.is_a?(Regexp)
1750
+ val
1751
+ else
1752
+ val = ".*#{val}" if prefix && !val.sub!(/\A(\^|\\A)/, '')
1753
+ Regexp.new("#{prefix}#{val == '*' ? '.+' : val}")
1754
+ end
1755
+ end
1756
+ end
1757
+
1747
1758
  def semver(val)
1748
1759
  return val if val[3]
1749
1760
 
@@ -1762,12 +1773,13 @@ module Squared
1762
1773
  end
1763
1774
 
1764
1775
  def semcmp(val, other)
1765
- a, b = [val, other].map! { |ver| ver.match(SEM_VER) }
1766
- return 1 unless a
1767
- return -1 unless b
1768
- return 0 if a[0] == b[0]
1776
+ return 0 if val == other
1769
1777
 
1770
- a, b = [a, b].map! { |c| [c[1], c[3], c[5] || '0'] }
1778
+ a, b = [val, other].map! { |ver| ver.scan(SEM_VER) }
1779
+ return -1 if b.empty?
1780
+ return 1 if a.empty?
1781
+
1782
+ a, b = [a.first, b.first].map! { |c| [c[0], c[2], c[4] || '0', c[5] ? '-1' : '0'] }
1771
1783
  a.each_with_index do |c, index|
1772
1784
  next if c == (d = b[index])
1773
1785
 
@@ -1776,6 +1788,10 @@ module Squared
1776
1788
  0
1777
1789
  end
1778
1790
 
1791
+ def semgte?(val, other)
1792
+ semcmp(val, other) != 1
1793
+ end
1794
+
1779
1795
  def indexitem(val)
1780
1796
  [$1.to_i, $2 && $2[1..-1]] if val =~ /\A[=^#{indexchar}](\d+)(:.+)?\z/
1781
1797
  end
@@ -1819,7 +1835,7 @@ module Squared
1819
1835
  def on(event, from, *args, **kwargs)
1820
1836
  return unless from && @events.key?(event)
1821
1837
 
1822
- @events[event][from]&.each do |obj|
1838
+ Array(@events[event][from]).each do |obj|
1823
1839
  target, opts = if obj.is_a?(Array) && obj[1].is_a?(Hash)
1824
1840
  [obj[0], kwargs.empty? ? obj[1] : obj[1].merge(kwargs)]
1825
1841
  else
@@ -1849,13 +1865,12 @@ module Squared
1849
1865
  pwd = Pathname.pwd
1850
1866
  if block_given?
1851
1867
  begin
1852
- pass = semscan(pass).join <= RUBY_VERSION if pass.is_a?(String)
1853
1868
  if (path == pwd || pass == true) && (workspace.mri? || !workspace.windows?)
1854
1869
  ret = yield
1855
1870
  else
1856
- Dir.chdir(path)
1871
+ Dir.chdir path
1857
1872
  ret = yield
1858
- Dir.chdir(pwd)
1873
+ Dir.chdir pwd
1859
1874
  end
1860
1875
  rescue StandardError => e
1861
1876
  on_error(e, from, dryrun: dryrun)
@@ -1878,8 +1893,8 @@ module Squared
1878
1893
  end
1879
1894
 
1880
1895
  def run_set(cmd, val = nil, opts: nil, **)
1881
- diso = @output[1] == false && !@output[0].nil?
1882
- dise = @output[2] == false
1896
+ noopt = @output[1] == false && !@output[0].nil?
1897
+ noenv = @output[2] == false
1883
1898
  parse = lambda do |data|
1884
1899
  ret = []
1885
1900
  if data[:command]
@@ -1899,8 +1914,8 @@ module Squared
1899
1914
  case cmd
1900
1915
  when Array
1901
1916
  @output = if cmd.all? { |data| data.is_a?(Hash) }
1902
- diso = false
1903
- dise = false
1917
+ noopt = false
1918
+ noenv = false
1904
1919
  cmd.map { |data| parse.call(data) }
1905
1920
  else
1906
1921
  cmd.dup
@@ -1911,14 +1926,14 @@ module Squared
1911
1926
  else
1912
1927
  @output[0] = cmd
1913
1928
  end
1914
- unless diso
1929
+ unless noopt
1915
1930
  if opts == false
1916
1931
  @output[1] = false
1917
1932
  elsif opts && opts != true
1918
1933
  @output[1] = opts
1919
1934
  end
1920
1935
  end
1921
- return if dise
1936
+ return if noenv
1922
1937
 
1923
1938
  if val.is_a?(Hash)
1924
1939
  @output[2] = val
@@ -2021,6 +2036,10 @@ module Squared
2021
2036
  @only ? !@only.include?(key) : @pass.include?(key)
2022
2037
  end
2023
2038
 
2039
+ def matchany?(val, list, empty: true)
2040
+ list.empty? ? empty : list.any? { |pat| val.match?(pat) }
2041
+ end
2042
+
2024
2043
  def projectpath?(val)
2025
2044
  val = Pathname.new(val).cleanpath
2026
2045
  val.absolute? ? val.to_s.start_with?(File.join(path, '')) : !val.to_s.start_with?(File.join('..', ''))