public void TestPossibleVersions()
        {
            Dependency dep = new Dependency("test", "artifact1", "2.0");

            // adding multiple versions to a concrete version results in only that one.
            dep.AddVersion("0.1");

            Assert.False(dep.HasPossibleVersions);

            dep.AddVersion("1.0");
            dep.AddVersion("2.0.0");
            dep.AddVersion("3.0");

            Assert.True(dep.HasPossibleVersions);

            Assert.True(dep.BestVersion == "2.0.0");

            dep.RemovePossibleVersion(dep.BestVersion);

            Assert.False(dep.HasPossibleVersions);

            dep = new Dependency("test", "artifact1", "2.0+");

            // check plus
            dep.AddVersion("1.0");
            dep.AddVersion("2.0.0");
            dep.AddVersion("2.0.1");
            dep.AddVersion("2.1");
            dep.AddVersion("3.0");

            Assert.True(dep.HasPossibleVersions);
            Assert.True(dep.BestVersion == "2.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.0.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.0.0");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.IsNullOrEmpty(dep.BestVersion);
            Assert.False(dep.HasPossibleVersions);

            dep = new Dependency("test", "artifact1", "2.0+");

            // check plus
            dep.AddVersion("3.0");
            dep.AddVersion("2.2.0");
            dep.AddVersion("2.0.1");
            dep.AddVersion("2.1");
            dep.AddVersion("1.0");

            Assert.True(dep.HasPossibleVersions);
            Assert.True(dep.BestVersion == "2.2.0");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.0.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.IsNullOrEmpty(dep.BestVersion);
            Assert.False(dep.HasPossibleVersions);
        }
        public void TestRefineVersionRange()
        {
            Dependency dep = new Dependency("test", "artifact1", "2.0+");

            dep.AddVersion("3.0");
            dep.AddVersion("2.2.0");
            dep.AddVersion("2.0.1");
            dep.AddVersion("2.1");
            dep.AddVersion("1.0");

            // refinement with the same object should have no effect.
            Assert.True(dep.RefineVersionRange(dep));
            Assert.True(dep.HasPossibleVersions);
            Assert.True(dep.BestVersion == "2.2.0");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.0.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.IsNullOrEmpty(dep.BestVersion);
            Assert.False(dep.HasPossibleVersions);

            // refinement with a concrete version not compatible should fail.
            dep = new Dependency("test", "artifact1", "2.0+");
           
            dep.AddVersion("3.0");
            dep.AddVersion("2.2.0");
            dep.AddVersion("2.0.1");
            dep.AddVersion("2.1");
            dep.AddVersion("1.0");

            Dependency dep1 = new Dependency("test", "artifact1", "3.0");

            Assert.False(dep.RefineVersionRange(dep1));
            Assert.False(dep.HasPossibleVersions);

            // concrete included
            dep = new Dependency("test", "artifact1", "2.0+");

            dep.AddVersion("3.0");
            dep.AddVersion("2.2.0");
            dep.AddVersion("2.0.1");
            dep.AddVersion("2.1");
            dep.AddVersion("1.0");

            Dependency dep2 = new Dependency("test", "artifact1", "2.1.0");

            Assert.True(dep.RefineVersionRange(dep2));
            Assert.True(dep.BestVersion == "2.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.False(dep.HasPossibleVersions);

            // check overlapping ranges
            dep = new Dependency("test", "artifact1", "2.0+");

            dep.AddVersion("3.0");
            dep.AddVersion("2.2.0");
            dep.AddVersion("2.0.1");
            dep.AddVersion("2.1");
            dep.AddVersion("1.0");

            Dependency dep1plus = new Dependency("test", "artifact1", "2.1+");

            Assert.True(dep.RefineVersionRange(dep1plus));
            Assert.True(dep.BestVersion == "2.2.0");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.False(dep.HasPossibleVersions);
        }
        public void TestPossibleVersions()
        {
            Dependency dep = new Dependency("test", "artifact1", "2.0");

            // adding multiple versions to a concrete version results in only that one.
           dep.AddVersion("0.1");

            Assert.False(dep.HasPossibleVersions);

            dep.AddVersion("1.0");
            dep.AddVersion("2.0.0");
            dep.AddVersion("3.0");

            Assert.True(dep.HasPossibleVersions);

            Assert.True(dep.BestVersion == "2.0.0");

            dep.RemovePossibleVersion(dep.BestVersion);

            Assert.False(dep.HasPossibleVersions);

            dep = new Dependency("test", "artifact1", "2.0+");

            // check plus
            dep.AddVersion("1.0");
            dep.AddVersion("2.0.0");
            dep.AddVersion("2.0.1");
            dep.AddVersion("2.1");
            dep.AddVersion("3.0");

            Assert.True(dep.HasPossibleVersions);
            Assert.True(dep.BestVersion == "2.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.0.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.0.0");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.IsNullOrEmpty(dep.BestVersion);
            Assert.False(dep.HasPossibleVersions);

            dep = new Dependency("test", "artifact1", "2.0+");

            // check plus
            dep.AddVersion("3.0");
            dep.AddVersion("2.2.0");
            dep.AddVersion("2.0.1");
            dep.AddVersion("2.1");
            dep.AddVersion("1.0");

            Assert.True(dep.HasPossibleVersions);
            Assert.True(dep.BestVersion == "2.2.0");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.0.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.IsNullOrEmpty(dep.BestVersion);
            Assert.False(dep.HasPossibleVersions);
        }
        public void TestRefineVersionRange()
        {
            Dependency dep = new Dependency("test", "artifact1", "2.0+");

            dep.AddVersion("3.0");
            dep.AddVersion("2.2.0");
            dep.AddVersion("2.0.1");
            dep.AddVersion("2.1");
            dep.AddVersion("1.0");

            // refinement with the same object should have no effect.
            Assert.True(dep.RefineVersionRange(dep));
            Assert.True(dep.HasPossibleVersions);
            Assert.True(dep.BestVersion == "2.2.0");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.0.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.IsNullOrEmpty(dep.BestVersion);
            Assert.False(dep.HasPossibleVersions);

            // refinement with a concrete version not compatible should fail.
            dep = new Dependency("test", "artifact1", "2.0+");

            dep.AddVersion("3.0");
            dep.AddVersion("2.2.0");
            dep.AddVersion("2.0.1");
            dep.AddVersion("2.1");
            dep.AddVersion("1.0");

            Dependency dep1 = new Dependency("test", "artifact1", "3.0");

            Assert.False(dep.RefineVersionRange(dep1));
            Assert.False(dep.HasPossibleVersions);

            // concrete included
            dep = new Dependency("test", "artifact1", "2.0+");

            dep.AddVersion("3.0");
            dep.AddVersion("2.2.0");
            dep.AddVersion("2.0.1");
            dep.AddVersion("2.1");
            dep.AddVersion("1.0");

            Dependency dep2 = new Dependency("test", "artifact1", "2.1.0");

            Assert.True(dep.RefineVersionRange(dep2));
            Assert.True(dep.BestVersion == "2.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.False(dep.HasPossibleVersions);

            // check overlapping ranges
            dep = new Dependency("test", "artifact1", "2.0+");

            dep.AddVersion("3.0");
            dep.AddVersion("2.2.0");
            dep.AddVersion("2.0.1");
            dep.AddVersion("2.1");
            dep.AddVersion("1.0");

            Dependency dep1plus = new Dependency("test", "artifact1", "2.1+");

            Assert.True(dep.RefineVersionRange(dep1plus));
            Assert.True(dep.BestVersion == "2.2.0");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.True(dep.BestVersion == "2.1");
            dep.RemovePossibleVersion(dep.BestVersion);
            Assert.False(dep.HasPossibleVersions);
        }
        /// <summary>
        /// Reads the maven metadata for an artifact.
        /// This reads the list of available versions.
        /// </summary>
        /// <param name="dep">Dependency to process</param>
        /// <param name="fname">file name of the metadata.</param>
        internal void ProcessMetadata(Dependency dep, string fname)
        {
            XmlTextReader reader = new XmlTextReader(new StreamReader(fname));

            bool inVersions = false;
            while (reader.Read())
            {
                if (reader.Name == "versions")
                {
                    inVersions = reader.IsStartElement();
                }
                else if (inVersions && reader.Name == "version")
                {
                    dep.AddVersion(reader.ReadString());
                }
            }
        }
        /// <summary>
        /// Copies the dependencies from the repository to the specified directory.
        /// The destination directory is checked for an existing version of the
        /// dependency before copying.  The OverwriteConfirmation delegate is
        /// called for the first existing file or directory.  If the delegate
        /// returns true, the old dependency is deleted and the new one copied.
        /// </summary>
        /// <param name="dependencies">The dependencies to copy.</param>
        /// <param name="destDirectory">Destination directory.</param>
        /// <param name="confirmer">Confirmer - the delegate for confirming overwriting.</param>
        public void CopyDependencies(
            Dictionary<string, Dependency> dependencies,
            string destDirectory,
            OverwriteConfirmation confirmer)
        {
            if (!Directory.Exists(destDirectory))
            {
                Directory.CreateDirectory(destDirectory);
            }

            foreach (Dependency dep in dependencies.Values)
            {
                // match artifact-*.  The - is important to distinguish art-1.0.0
                // from artifact-1.0.0 (or base and basement).
                string[] dups = Directory.GetFileSystemEntries(destDirectory,
                                                               dep.Artifact + "-*");
                bool doCopy = true;
                bool doCleanup = false;
                foreach (string s in dups)
                {
                    // skip the .meta files (a little Unity creeps in).
                    if (s.EndsWith(".meta"))
                    {
                        continue;
                    }

                    // Strip the package extension from filenames.  Directories generated from
                    // unpacked AARs do not have extensions.
                    string existing = Directory.Exists(s) ? s :
                        Path.GetFileNameWithoutExtension(s);

                    // Extract the version from the filename.
                    // dep.Artifact is the name of the package (prefix)
                    // The regular expression extracts the version number from the filename
                    // handling filenames like foo-1.2.3-alpha.
                    string artifactName = existing.Substring(dep.Artifact.Length + 1);
                    System.Text.RegularExpressions.Match match =
                        System.Text.RegularExpressions.Regex.Match(artifactName, "^([0-9.]+)");
                    if (!match.Success) continue;
                    string artifactVersion = match.Groups[1].Value;

                    Dependency oldDep = new Dependency(dep.Group, artifactName, artifactVersion,
                                                       packageIds: dep.PackageIds,
                                                       repositories: dep.Repositories);

                    // add the artifact version so BestVersion == version.
                    oldDep.AddVersion(oldDep.Version);
                    // If the existing artifact matches the new dependency, don't modify it.
                    if (dep.Key == oldDep.Key) continue;
                    doCleanup = doCleanup || confirmer == null || confirmer(oldDep, dep);

                    if (doCleanup)
                    {
                        DeleteExistingFileOrDirectory(s);
                    }
                    else
                    {
                        doCopy = false;
                    }
                }

                if (doCopy)
                {
                    string aarFile = null;

                    // TODO(wilkinsonclay): get the extension from the pom file.
                    string baseName = null;
                    string extension = null;
                    foreach (string ext in Packaging)
                    {
                        string fname = Path.Combine(dep.BestVersionPath,
                            dep.Artifact + "-" + dep.BestVersion + ext);
                        if (File.Exists(fname))
                        {
                            baseName = dep.Artifact + "-" + dep.BestVersion;
                            aarFile = fname;
                            extension = ext;
                        }
                    }

                    if (aarFile != null)
                    {
                        string destName = Path.Combine(destDirectory, baseName) +
                            (extension == ".srcaar" ? ".aar" : extension);
                        string destNameUnpacked = Path.Combine(
                            destDirectory, Path.GetFileNameWithoutExtension(destName));
                        string existingName =
                            File.Exists(destName) ? destName :
                            Directory.Exists(destNameUnpacked) ? destNameUnpacked : null;

                        if (existingName != null)
                        {
                            doCopy = File.GetLastWriteTime(existingName).CompareTo(
                                File.GetLastWriteTime(aarFile)) < 0;
                            if (doCopy) DeleteExistingFileOrDirectory(existingName);
                        }
                        if (doCopy)
                        {
                            File.Copy(aarFile, destName);
                        }
                    }
                    else
                    {
                        throw new ResolutionException("Cannot find artifact for " +
                            dep);
                    }
                }
            }
        }