Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Gemfile.lock
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
PATH
remote: .
specs:
parse_packwerk (0.14.0)
parse_packwerk (0.15.0)
sorbet-runtime

GEM
Expand Down
10 changes: 5 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,15 +10,15 @@ packages = ParsePackwerk.all
# Get a single package with a given ame
package = ParsePackwerk.find('packs/my_pack')

# Get a structured `deprecated_references.yml` object a single package
deprecated_references = ParsePackwerk::DeprecatedReferences.for(package)
# Get a structured `package_todo.yml` object a single package
package_todo = ParsePackwerk::PackageTodo.for(package)

# Count violations of a particular type for a package
deprecated_references.violations.count(&:privacy?)
deprecated_references.violations.count(&:dependency?)
package_todo.violations.count(&:privacy?)
package_todo.violations.count(&:dependency?)

# Get the number of files a particular constant is violated in
deprecated_references.violations.select { |v| v.class_name == 'SomeConstant' }.sum { |v| v.files.count }
package_todo.violations.select { |v| v.class_name == 'SomeConstant' }.sum { |v| v.files.count }
```

# Why does this gem exist?
Expand Down
2 changes: 1 addition & 1 deletion lib/parse_packwerk.rb
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
require 'pathname'
require 'parse_packwerk/constants'
require 'parse_packwerk/violation'
require 'parse_packwerk/deprecated_references'
require 'parse_packwerk/package_todo'
require 'parse_packwerk/package'
require 'parse_packwerk/configuration'
require 'parse_packwerk/package_set'
Expand Down
2 changes: 1 addition & 1 deletion lib/parse_packwerk/constants.rb
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ module ParsePackwerk
ROOT_PACKAGE_NAME = T.let('.'.freeze, String)
PACKAGE_YML_NAME = T.let('package.yml'.freeze, String)
PACKWERK_YML_NAME = T.let('packwerk.yml'.freeze, String)
DEPRECATED_REFERENCES_YML_NAME = T.let('deprecated_references.yml'.freeze, String)
PACKAGE_TODO_YML_NAME = T.let('package_todo.yml'.freeze, String)
ENFORCE_DEPENDENCIES = T.let('enforce_dependencies'.freeze, String)
ENFORCE_PRIVACY = T.let('enforce_privacy'.freeze, String)
PUBLIC_PATH = T.let('public_path'.freeze, String)
Expand Down
2 changes: 1 addition & 1 deletion lib/parse_packwerk/package.rb
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ def enforces_privacy?

sig { returns(T::Array[Violation]) }
def violations
DeprecatedReferences.for(self).violations
PackageTodo.for(self).violations
end
end
end
Original file line number Diff line number Diff line change
@@ -1,33 +1,33 @@
# typed: strict

module ParsePackwerk
class DeprecatedReferences < T::Struct
class PackageTodo < T::Struct
extend T::Sig

const :pathname, Pathname
const :violations, T::Array[Violation]

sig { params(package: Package).returns(DeprecatedReferences) }
sig { params(package: Package).returns(PackageTodo) }
def self.for(package)
deprecated_references_yml_pathname = package.directory.join(DEPRECATED_REFERENCES_YML_NAME)
DeprecatedReferences.from(deprecated_references_yml_pathname)
package_todo_yml_pathname = package.directory.join(PACKAGE_TODO_YML_NAME)
PackageTodo.from(package_todo_yml_pathname)
end

sig { params(pathname: Pathname).returns(DeprecatedReferences) }
sig { params(pathname: Pathname).returns(PackageTodo) }
def self.from(pathname)
if !pathname.exist?
new(
pathname: pathname.cleanpath,
violations: []
)
else
deprecated_references_loaded_yml = YAML.load_file(pathname)
package_todo_loaded_yml = YAML.load_file(pathname)

all_violations = []
deprecated_references_loaded_yml&.each_key do |to_package_name|
deprecated_references_per_package = deprecated_references_loaded_yml[to_package_name]
deprecated_references_per_package.each_key do |class_name|
symbol_usage = deprecated_references_per_package[class_name]
package_todo_loaded_yml&.each_key do |to_package_name|
package_todo_per_package = package_todo_loaded_yml[to_package_name]
package_todo_per_package.each_key do |class_name|
symbol_usage = package_todo_per_package[class_name]
files = symbol_usage['files']
violations = symbol_usage['violations']
if violations.include? 'dependency'
Expand Down
2 changes: 1 addition & 1 deletion parse_packwerk.gemspec
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
Gem::Specification.new do |spec|
spec.name = "parse_packwerk"
spec.version = '0.14.0'
spec.version = '0.15.0'
spec.authors = ['Gusto Engineers']
spec.email = ['dev@gusto.com']
spec.summary = 'A low-dependency gem for parsing and writing packwerk YML files'
Expand Down
76 changes: 38 additions & 38 deletions spec/parse_packwerk_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -63,8 +63,8 @@ def hashify_violation(v)
)
end

let(:expected_deprecated_references) do
ParsePackwerk::DeprecatedReferences.from(Pathname.new('deprecated_references.yml'))
let(:expected_package_todo) do
ParsePackwerk::PackageTodo.from(Pathname.new('package_todo.yml'))
end

it 'correctly finds the package YML' do
Expand All @@ -75,7 +75,7 @@ def hashify_violation(v)
expect(expected_package.directory).to eq Pathname.new('.')
end

it { is_expected.to have_matching_package expected_package, expected_deprecated_references }
it { is_expected.to have_matching_package expected_package, expected_package_todo }
end

context 'in app that enforces privacy and dependencies' do
Expand Down Expand Up @@ -119,11 +119,11 @@ def hashify_violation(v)
)
end

let(:expected_root_deprecated_references) do
ParsePackwerk::DeprecatedReferences.from(Pathname.new('deprecated_references.yml'))
let(:expected_root_package_todo) do
ParsePackwerk::PackageTodo.from(Pathname.new('package_todo.yml'))
end

it { is_expected.to have_matching_package expected_root_package, expected_root_deprecated_references }
it { is_expected.to have_matching_package expected_root_package, expected_root_package_todo }

let(:expected_domain_package) do
ParsePackwerk::Package.new(
Expand All @@ -135,8 +135,8 @@ def hashify_violation(v)
)
end

let(:expected_domain_package_deprecated_references) do
ParsePackwerk::DeprecatedReferences.from(Pathname.new('packs/package_1/deprecated_references.yml'))
let(:expected_domain_package_package_todo) do
ParsePackwerk::PackageTodo.from(Pathname.new('packs/package_1/package_todo.yml'))
end

it 'correctly finds the package YML' do
Expand All @@ -147,7 +147,7 @@ def hashify_violation(v)
expect(expected_domain_package.directory).to eq Pathname.new('packs/package_1')
end

it { is_expected.to have_matching_package expected_domain_package, expected_domain_package_deprecated_references }
it { is_expected.to have_matching_package expected_domain_package, expected_domain_package_package_todo }
end

context 'in app that has public_path' do
Expand Down Expand Up @@ -193,11 +193,11 @@ def hashify_violation(v)
)
end

let(:expected_root_deprecated_refereces) do
ParsePackwerk::DeprecatedReferences.from(Pathname.new('deprecated_references.yml'))
let(:expected_root_package_todo) do
ParsePackwerk::PackageTodo.from(Pathname.new('package_todo.yml'))
end

it { is_expected.to have_matching_package expected_root_package, expected_root_deprecated_refereces }
it { is_expected.to have_matching_package expected_root_package, expected_root_package_todo }

let(:expected_domain_package) do
ParsePackwerk::Package.new(
Expand All @@ -210,11 +210,11 @@ def hashify_violation(v)
)
end

let(:expected_deprecated_references) do
ParsePackwerk::DeprecatedReferences.from(Pathname.new('packs/package_1/deprecated_references.yml'))
let(:expected_package_todo) do
ParsePackwerk::PackageTodo.from(Pathname.new('packs/package_1/package_todo.yml'))
end

it { is_expected.to have_matching_package expected_domain_package, expected_deprecated_references }
it { is_expected.to have_matching_package expected_domain_package, expected_package_todo }
end

context 'in app that has metadata' do
Expand Down Expand Up @@ -263,11 +263,11 @@ def hashify_violation(v)
)
end

let(:expected_root_deprecated_refereces) do
ParsePackwerk::DeprecatedReferences.from(Pathname.new('deprecated_references.yml'))
let(:expected_root_package_todo) do
ParsePackwerk::PackageTodo.from(Pathname.new('package_todo.yml'))
end

it { is_expected.to have_matching_package expected_root_package, expected_root_deprecated_refereces }
it { is_expected.to have_matching_package expected_root_package, expected_root_package_todo }

let(:expected_domain_package) do
ParsePackwerk::Package.new(
Expand All @@ -284,16 +284,16 @@ def hashify_violation(v)
)
end

let(:expected_deprecated_references) do
ParsePackwerk::DeprecatedReferences.from(Pathname.new('packs/package_1/deprecated_references.yml'))
let(:expected_package_todo) do
ParsePackwerk::PackageTodo.from(Pathname.new('packs/package_1/package_todo.yml'))
end

it { is_expected.to have_matching_package expected_domain_package, expected_deprecated_references }
it { is_expected.to have_matching_package expected_domain_package, expected_package_todo }
end

context 'in app that has violations' do
before do
write_file('packs/package_2/deprecated_references.yml', <<~CONTENTS)
write_file('packs/package_2/package_todo.yml', <<~CONTENTS)
# This file contains a list of dependencies that are not part of the long term plan for ..
# We should generally work to reduce this list, but not at the expense of actually getting work done.
#
Expand Down Expand Up @@ -325,7 +325,7 @@ def hashify_violation(v)
enforce_privacy: true
CONTENTS

write_file('packs/package_1/deprecated_references.yml', <<~CONTENTS)
write_file('packs/package_1/package_todo.yml', <<~CONTENTS)
# This file contains a list of dependencies that are not part of the long term plan for ..
# We should generally work to reduce this list, but not at the expense of actually getting work done.
#
Expand All @@ -348,7 +348,7 @@ def hashify_violation(v)
- packs/package_2
CONTENTS

write_file('deprecated_references.yml', <<~CONTENTS)
write_file('package_todo.yml', <<~CONTENTS)
# This file contains a list of dependencies that are not part of the long term plan for ..
# We should generally work to reduce this list, but not at the expense of actually getting work done.
#
Expand Down Expand Up @@ -407,9 +407,9 @@ def hashify_violation(v)
)
end

let(:expected_deprecated_references) do
ParsePackwerk::DeprecatedReferences.new(
pathname: Pathname.new('deprecated_references.yml'),
let(:expected_package_todo) do
ParsePackwerk::PackageTodo.new(
pathname: Pathname.new('package_todo.yml'),
violations: [
ParsePackwerk::Violation.new(
type: 'dependency',
Expand All @@ -427,7 +427,7 @@ def hashify_violation(v)
)
end

it { is_expected.to have_matching_package expected_root_package, expected_deprecated_references }
it { is_expected.to have_matching_package expected_root_package, expected_package_todo }

let(:expected_domain_package_1) do
ParsePackwerk::Package.new(
Expand All @@ -439,9 +439,9 @@ def hashify_violation(v)
)
end

let(:expected_deprecated_references_1) do
ParsePackwerk::DeprecatedReferences.new(
pathname: Pathname.new('packs/package_1/deprecated_references.yml'),
let(:expected_package_todo_1) do
ParsePackwerk::PackageTodo.new(
pathname: Pathname.new('packs/package_1/package_todo.yml'),
violations: [
ParsePackwerk::Violation.new(
type: 'privacy',
Expand All @@ -453,7 +453,7 @@ def hashify_violation(v)
)
end

it { is_expected.to have_matching_package expected_domain_package_1, expected_deprecated_references_1 }
it { is_expected.to have_matching_package expected_domain_package_1, expected_package_todo_1 }

let(:expected_domain_package_2) do
ParsePackwerk::Package.new(
Expand All @@ -465,9 +465,9 @@ def hashify_violation(v)
)
end

let(:expected_domain_package_deprecated_references_2) do
ParsePackwerk::DeprecatedReferences.new(
pathname: Pathname.new('packs/package_2/deprecated_references.yml'),
let(:expected_domain_package_package_todo_2) do
ParsePackwerk::PackageTodo.new(
pathname: Pathname.new('packs/package_2/package_todo.yml'),
violations: [
ParsePackwerk::Violation.new(
type: 'dependency',
Expand All @@ -491,7 +491,7 @@ def hashify_violation(v)
)
end

it { is_expected.to have_matching_package expected_domain_package_2, expected_domain_package_deprecated_references_2 }
it { is_expected.to have_matching_package expected_domain_package_2, expected_domain_package_package_todo_2 }
end

context 'in an app that has specified package paths' do
Expand Down Expand Up @@ -636,7 +636,7 @@ def hashify_violation(v)
enforce_privacy: true
CONTENTS

write_file('packs/my_pack/deprecated_references.yml', <<~CONTENTS)
write_file('packs/my_pack/package_todo.yml', <<~CONTENTS)
# This file contains a list of dependencies that are not part of the long term plan for ..
# We should generally work to reduce this list, but not at the expense of actually getting work done.
#
Expand Down Expand Up @@ -881,7 +881,7 @@ def hashify_violation(v)
describe 'ParsePackwerk.write_package_yml' do
let(:package_dir) { Pathname.new('packs/example_pack') }
let(:package_yml) { package_dir.join('package.yml') }
let(:deprecated_references_yml) { package_dir.join('deprecated_references.yml') }
let(:package_todo_yml) { package_dir.join('package_todo.yml') }

def build_pack(public_path: 'app/public', dependencies: [], metadata: {})
ParsePackwerk::Package.new(
Expand Down
16 changes: 8 additions & 8 deletions spec/support/have_matching_package.rb
Original file line number Diff line number Diff line change
@@ -1,28 +1,28 @@
RSpec::Matchers.define(:have_matching_package) do |expected_package, expected_deprecated_references|
RSpec::Matchers.define(:have_matching_package) do |expected_package, expected_package_todo|
match do |actual_packages|
@actual_packages = actual_packages
@expected_package = expected_package
@actual_package = actual_packages.find{|actual_package| actual_package.name == expected_package.name}
@actual_deprecated_references = @actual_package && ParsePackwerk::DeprecatedReferences.for(@actual_package)
@hashified_expected = deep_hashify_package(expected_package, expected_deprecated_references)
@hashified_actual = deep_hashify_package(@actual_package, @actual_deprecated_references)
@actual_package_todo = @actual_package && ParsePackwerk::PackageTodo.for(@actual_package)
@hashified_expected = deep_hashify_package(expected_package, expected_package_todo)
@hashified_actual = deep_hashify_package(@actual_package, @actual_package_todo)
!@actual_package.nil? && @hashified_expected == @hashified_actual
end

description do
"to have a package named #{expected_package.package_name.inspect} with identical attributes"
end

def deep_hashify_package(package, deprecated_references)
def deep_hashify_package(package, package_todo)
{
name: package.name,
enforce_dependencies: package.enforce_dependencies,
enforce_privacy: package.enforce_privacy,
metadata: package.metadata,
dependencies: package.dependencies.sort,
deprecated_references: deprecated_references.nil? ? {} : {
pathname: deprecated_references.pathname.to_s,
violations: hashify_violations(deprecated_references.violations)
package_todo: package_todo.nil? ? {} : {
pathname: package_todo.pathname.to_s,
violations: hashify_violations(package_todo.violations)
}
}
end
Expand Down