Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1485)

Side by Side Diff: lib/src/version_range.dart

Issue 1127783002: Add more set-like version constraint operations. (Closed) Base URL: git@github.com:dart-lang/pub_semver@master
Patch Set: Code review changes Created 5 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « lib/src/version_constraint.dart ('k') | lib/src/version_union.dart » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 library pub_semver.src.version_range; 5 library pub_semver.src.version_range;
6 6
7 import 'version.dart'; 7 import 'version.dart';
8 import 'version_constraint.dart'; 8 import 'version_constraint.dart';
9 import 'version_union.dart';
9 10
10 /// Constrains versions to a fall within a given range. 11 /// Constrains versions to a fall within a given range.
11 /// 12 ///
12 /// If there is a minimum, then this only allows versions that are at that 13 /// If there is a minimum, then this only allows versions that are at that
13 /// minimum or greater. If there is a maximum, then only versions less than 14 /// minimum or greater. If there is a maximum, then only versions less than
14 /// that are allowed. In other words, this allows `>= min, < max`. 15 /// that are allowed. In other words, this allows `>= min, < max`.
15 class VersionRange implements VersionConstraint { 16 class VersionRange implements VersionConstraint {
16 /// The minimum end of the range. 17 /// The minimum end of the range.
17 /// 18 ///
18 /// If [includeMin] is `true`, this will be the minimum allowed version. 19 /// If [includeMin] is `true`, this will be the minimum allowed version.
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after
92 !max.isPreRelease && other.isPreRelease && 93 !max.isPreRelease && other.isPreRelease &&
93 other.major == max.major && other.minor == max.minor && 94 other.major == max.major && other.minor == max.minor &&
94 other.patch == max.patch) { 95 other.patch == max.patch) {
95 return false; 96 return false;
96 } 97 }
97 } 98 }
98 99
99 return true; 100 return true;
100 } 101 }
101 102
103 bool allowsAll(VersionConstraint other) {
104 if (other.isEmpty) return true;
105 if (other is Version) return allows(other);
106
107 if (other is VersionUnion) {
108 return other.constraints.every((constraint) => allowsAll(constraint));
109 }
110
111 if (other is VersionRange) {
112 if (min != null) {
113 if (other.min == null) return false;
114 if (min > other.min) return false;
115 if (min == other.min && !includeMin && other.includeMin) return false;
116 }
117
118 if (max != null) {
119 if (other.max == null) return false;
120 if (max < other.max) return false;
121 if (max == other.max && !includeMax && other.includeMax) return false;
122 }
123
124 return true;
125 }
126
127 throw new ArgumentError('Unknown VersionConstraint type $other.');
128 }
129
130 bool allowsAny(VersionConstraint other) {
131 if (other.isEmpty) return false;
132 if (other is Version) return allows(other);
133
134 if (other is VersionUnion) {
135 return other.constraints.any((constraint) => allowsAny(constraint));
136 }
137
138 if (other is VersionRange) {
139 // If neither range has a minimum, they'll overlap at some point.
140 //
141 // ... this ]
142 // ... other ]
143 if (min == null && other.min == null) return true;
144
145 // If this range has a lower minimum than the other range, it overlaps as
146 // long as its maximum is higher than or the same as the other range's
147 // minimum.
148 //
149 // [ this ] [ this ]
150 // [ other ] [ other ]
151 if (min == null || (other.min != null && min < other.min)) {
152 if (max == null) return true;
153 if (max > other.min) return true;
154 if (max < other.min) return false;
155 assert(max == other.min);
156 return includeMax && other.includeMin;
157 }
158
159 // If this range has a higher minimum than the other range, it overlaps as
160 // long as its minimum is lower than or the same as the other range's
161 // maximum.
162 //
163 // [ this ] [ this ]
164 // [ other ] [ other ]
Bob Nystrom 2015/05/06 17:30:58 <3 the art.
165 if (other.max == null) return true;
166 if (min < other.max) return true;
167 if (min > other.max) return false;
168 assert(min == other.max);
169 return includeMin && other.includeMax;
170 }
171
172 throw new ArgumentError('Unknown VersionConstraint type $other.');
173 }
174
102 VersionConstraint intersect(VersionConstraint other) { 175 VersionConstraint intersect(VersionConstraint other) {
103 if (other.isEmpty) return other; 176 if (other.isEmpty) return other;
177 if (other is VersionUnion) return other.intersect(this);
104 178
105 // A range and a Version just yields the version if it's in the range. 179 // A range and a Version just yields the version if it's in the range.
106 if (other is Version) { 180 if (other is Version) {
107 return allows(other) ? other : VersionConstraint.empty; 181 return allows(other) ? other : VersionConstraint.empty;
108 } 182 }
109 183
110 if (other is VersionRange) { 184 if (other is VersionRange) {
111 // Intersect the two ranges. 185 // Intersect the two ranges.
112 var intersectMin = min; 186 var intersectMin = min;
113 var intersectIncludeMin = includeMin; 187 var intersectIncludeMin = includeMin;
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after
155 } 229 }
156 230
157 // If we got here, there is an actual range. 231 // If we got here, there is an actual range.
158 return new VersionRange(min: intersectMin, max: intersectMax, 232 return new VersionRange(min: intersectMin, max: intersectMax,
159 includeMin: intersectIncludeMin, includeMax: intersectIncludeMax); 233 includeMin: intersectIncludeMin, includeMax: intersectIncludeMax);
160 } 234 }
161 235
162 throw new ArgumentError('Unknown VersionConstraint type $other.'); 236 throw new ArgumentError('Unknown VersionConstraint type $other.');
163 } 237 }
164 238
239 VersionConstraint union(VersionConstraint other) {
240 if (other is Version) {
241 if (allows(other)) return this;
242
243 if (other == min) {
244 return new VersionRange(
245 min: this.min, max: this.max,
246 includeMin: true, includeMax: this.includeMax);
247 }
248
249 if (other == max) {
250 return new VersionRange(
251 min: this.min, max: this.max,
252 includeMin: this.includeMin, includeMax: true);
253 }
254
255 return new VersionConstraint.unionOf([this, other]);
256 }
257
258 if (other is VersionRange) {
259 // If the two ranges don't overlap, we won't be able to create a single
260 // VersionRange for both of them.
261 var edgesTouch = (max == other.min && (includeMax || other.includeMin)) ||
262 (min == other.max && (includeMin || other.includeMax));
263 if (!edgesTouch && !allowsAny(other)) {
264 return new VersionConstraint.unionOf([this, other]);
265 }
266
267 var unionMin = min;
268 var unionIncludeMin = includeMin;
269 var unionMax = max;
270 var unionIncludeMax = includeMax;
271
272 if (unionMin == null) {
273 // Do nothing.
274 } else if (other.min == null || other.min < min) {
275 unionMin = other.min;
276 unionIncludeMin = other.includeMin;
277 } else if (min == other.min && other.includeMin) {
278 // If the edges are the same but one is inclusive, make it inclusive.
279 unionIncludeMin = true;
280 }
281
282 if (unionMax == null) {
283 // Do nothing.
284 } else if (other.max == null || other.max > max) {
285 unionMax = other.max;
286 unionIncludeMax = other.includeMax;
287 } else if (max == other.max && other.includeMax) {
288 // If the edges are the same but one is inclusive, make it inclusive.
289 unionIncludeMax = true;
290 }
291
292 return new VersionRange(min: unionMin, max: unionMax,
293 includeMin: unionIncludeMin, includeMax: unionIncludeMax);
294 }
295
296 return new VersionConstraint.unionOf([this, other]);
297 }
298
165 String toString() { 299 String toString() {
166 var buffer = new StringBuffer(); 300 var buffer = new StringBuffer();
167 301
168 if (min != null) { 302 if (min != null) {
169 buffer.write(includeMin ? '>=' : '>'); 303 buffer.write(includeMin ? '>=' : '>');
170 buffer.write(min); 304 buffer.write(min);
171 } 305 }
172 306
173 if (max != null) { 307 if (max != null) {
174 if (min != null) buffer.write(' '); 308 if (min != null) buffer.write(' ');
175 buffer.write(includeMax ? '<=' : '<'); 309 buffer.write(includeMax ? '<=' : '<');
176 buffer.write(max); 310 buffer.write(max);
177 } 311 }
178 312
179 if (min == null && max == null) buffer.write('any'); 313 if (min == null && max == null) buffer.write('any');
180 return buffer.toString(); 314 return buffer.toString();
181 } 315 }
182 } 316 }
OLDNEW
« no previous file with comments | « lib/src/version_constraint.dart ('k') | lib/src/version_union.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698