1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
|
# frozen_string_literal: true
require 'spec_helper'
RSpec.describe ::API::Helpers::Packages::Npm, feature_category: :package_registry do # rubocop: disable RSpec/FilePath
let(:object) { klass.new(params) }
let(:klass) do
Struct.new(:params) do
include ::API::Helpers
include ::API::Helpers::Packages::Npm
end
end
let_it_be(:user) { create(:user) }
let_it_be(:group) { create(:group) }
let_it_be(:namespace) { group }
let_it_be(:project) { create(:project, :public, namespace: namespace) }
let_it_be(:package) { create(:npm_package, project: project) }
describe '#endpoint_scope' do
subject { object.endpoint_scope }
context 'when params includes an id' do
let(:params) { { id: 42, package_name: 'foo' } }
it { is_expected.to eq(:project) }
end
context 'when params does not include an id' do
let(:params) { { package_name: 'foo' } }
it { is_expected.to eq(:instance) }
end
end
describe '#finder_for_endpoint_scope' do
subject { object.finder_for_endpoint_scope(package_name) }
let(:package_name) { package.name }
context 'when called with project scope' do
let(:params) { { id: project.id } }
it 'returns a PackageFinder for project scope' do
expect(::Packages::Npm::PackageFinder).to receive(:new).with(package_name, project: project)
subject
end
end
context 'when called with instance scope' do
let(:params) { { package_name: package_name } }
it 'returns a PackageFinder for namespace scope' do
expect(::Packages::Npm::PackageFinder).to receive(:new).with(package_name, namespace: group)
subject
end
end
end
describe '#project_id_or_nil' do
subject { object.project_id_or_nil }
context 'when called with project scope' do
let(:params) { { id: project.id } }
it { is_expected.to eq(project.id) }
end
context 'when called with namespace scope' do
context 'when given an unscoped name' do
let(:params) { { package_name: 'foo' } }
it { is_expected.to eq(nil) }
end
context 'when given a scope that does not match a group name' do
let(:params) { { package_name: '@nonexistent-group/foo' } }
it { is_expected.to eq(nil) }
end
context 'when given a scope that matches a group name' do
let(:params) { { package_name: package.name } }
it { is_expected.to eq(project.id) }
context 'with another package with the same name, in another project in the namespace' do
let_it_be(:project2) { create(:project, :public, namespace: namespace) }
let_it_be(:package2) { create(:npm_package, name: package.name, project: project2) }
it 'returns the project id for the newest matching package within the scope' do
expect(subject).to eq(project2.id)
end
end
end
context 'with npm_allow_packages_in_multiple_projects disabled' do
before do
stub_feature_flags(npm_allow_packages_in_multiple_projects: false)
end
context 'when given an unscoped name' do
let(:params) { { package_name: 'foo' } }
it { is_expected.to eq(nil) }
end
context 'when given a scope that does not match a group name' do
let(:params) { { package_name: '@nonexistent-group/foo' } }
it { is_expected.to eq(nil) }
end
context 'when given a scope that matches a group name' do
let(:params) { { package_name: package.name } }
it { is_expected.to eq(project.id) }
context 'with another package with the same name, in another project in the namespace' do
let_it_be(:project2) { create(:project, :public, namespace: namespace) }
let_it_be(:package2) { create(:npm_package, name: package.name, project: project2) }
it 'returns the project id for the newest matching package within the scope' do
expect(subject).to eq(project2.id)
end
end
end
end
end
end
end
|