version.dart 3.09 KB
Newer Older
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
// Copyright 2017 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

class Version implements Comparable<Version> {
  static final RegExp versionPattern =
      new RegExp(r'^(\d+)(\.(\d+)(\.(\d+))?)?');

  /// The major version number: "1" in "1.2.3".
  final int major;

  /// The minor version number: "2" in "1.2.3".
  final int minor;

  /// The patch version number: "3" in "1.2.3".
  final int patch;

  /// The original string representation of the version number.
  ///
  /// This preserves textual artifacts like leading zeros that may be left out
  /// of the parsed version.
  final String _text;

  /// Creates a new [Version] object.
  factory Version(int major, int minor, int patch, {String text}) {
    if (text == null) {
      text = major == null ? '0' : '$major';
28 29 30 31
      if (minor != null)
        text = '$text.$minor';
      if (patch != null)
        text = '$text.$patch';
32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47
    }

    return new Version._(major ?? 0, minor ?? 0, patch ?? 0, text);
  }

  Version._(this.major, this.minor, this.patch, this._text) {
    if (major < 0)
      throw new ArgumentError('Major version must be non-negative.');
    if (minor < 0)
      throw new ArgumentError('Minor version must be non-negative.');
    if (patch < 0)
      throw new ArgumentError('Patch version must be non-negative.');
  }

  /// Creates a new [Version] by parsing [text].
  factory Version.parse(String text) {
48
    final Match match = versionPattern.firstMatch(text ?? '');
49
    if (match == null) {
50
      return null;
51 52 53
    }

    try {
54 55 56
      final int major = int.parse(match[1] ?? '0');
      final int minor = int.parse(match[3] ?? '0');
      final int patch = int.parse(match[5] ?? '0');
57 58
      return new Version._(major, minor, patch, text);
    } on FormatException {
59
      return null;
60 61 62
    }
  }

63 64 65 66 67 68 69 70 71 72 73 74 75 76
  /// Returns the primary version out of a list of candidates.
  ///
  /// This is the highest-numbered stable version.
  static Version primary(List<Version> versions) {
    Version primary;
    for (Version version in versions) {
      if (primary == null || (version > primary)) {
        primary = version;
      }
    }
    return primary;
  }


77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97
  static Version get unknown => new Version(0, 0, 0, text: 'unknown');

  /// Two [Version]s are equal if their version numbers are. The version text
  /// is ignored.
  @override
  bool operator ==(dynamic other) {
    if (other is! Version)
      return false;
    return major == other.major && minor == other.minor && patch == other.patch;
  }

  @override
  int get hashCode => major ^ minor ^ patch;

  bool operator <(Version other) => compareTo(other) < 0;
  bool operator >(Version other) => compareTo(other) > 0;
  bool operator <=(Version other) => compareTo(other) <= 0;
  bool operator >=(Version other) => compareTo(other) >= 0;

  @override
  int compareTo(Version other) {
98 99 100 101
    if (major != other.major)
      return major.compareTo(other.major);
    if (minor != other.minor)
      return minor.compareTo(other.minor);
102 103 104 105 106 107
    return patch.compareTo(other.patch);
  }

  @override
  String toString() => _text;
}