예제 #1
0
        public Package CreatePackage(IPackage nugetPackage, User currentUser)
        {
            ValidateNuGetPackage(nugetPackage);

            var packageRegistration = CreateOrGetPackageRegistration(currentUser, nugetPackage);

            var package = CreatePackageFromNuGetPackage(packageRegistration, nugetPackage);

            packageRegistration.Packages.Add(package);

            using (var tx = new TransactionScope())
            {
                using (var stream = nugetPackage.GetStream())
                {
                    UpdateIsLatest(packageRegistration);
                    packageRegistrationRepo.CommitChanges();
                    packageFileSvc.SavePackageFile(package, stream);
                    tx.Complete();
                }
            }

            NotifyIndexingService();

            return(package);
        }
예제 #2
0
        public Package CreatePackage(IPackage nugetPackage, User currentUser)
        {
            ValidateNuGetPackage(nugetPackage);

            var packageRegistration = CreateOrGetPackageRegistration(currentUser, nugetPackage);

            var package = CreatePackageFromNuGetPackage(packageRegistration, nugetPackage);

            packageRegistration.Packages.Add(package);

            using (var tx = new TransactionScope())
            {
                using (var stream = nugetPackage.GetStream())
                {
                    UpdateIsLatest(packageRegistration);
                    packageRegistrationRepo.CommitChanges();
                    packageFileSvc.SavePackageFile(package, stream);
                    tx.Complete();
                }
            }

            if (package.Status != PackageStatusType.Approved && package.Status != PackageStatusType.Exempted)
            {
                NotifyForModeration(package, comments: string.Empty);
            }

            NotifyIndexingService();

            return(package);
        }
예제 #3
0
        public async Task SoftDeletePackagesAsync(IEnumerable <Package> packages, User deletedBy, string reason, string signature)
        {
            EntitiesConfiguration.SuspendExecutionStrategy = true;
            using (var transaction = _entitiesContext.GetDatabase().BeginTransaction())
            {
                // Increase command timeout
                _entitiesContext.SetCommandTimeout(seconds: 300);

                // Keep package registrations
                var packageRegistrations = packages
                                           .GroupBy(p => p.PackageRegistration)
                                           .Select(g => g.First().PackageRegistration)
                                           .ToList();

                // Backup the package binaries and remove from main storage
                // We're doing this early in the process as we need the metadata to still exist in the DB.
                await BackupPackageBinaries(packages);

                // Store the soft delete in the database
                var packageDelete = new PackageDelete
                {
                    DeletedOn = DateTime.UtcNow,
                    DeletedBy = deletedBy,
                    Reason    = reason,
                    Signature = signature
                };

                foreach (var package in packages)
                {
                    package.Listed  = false;
                    package.Deleted = true;
                    packageDelete.Packages.Add(package);

                    await _auditingService.SaveAuditRecord(CreateAuditRecord(package, package.PackageRegistration, PackageAuditAction.SoftDeleted, reason));
                }

                _packageDeletesRepository.InsertOnCommit(packageDelete);

                // Update latest versions
                UpdateIsLatest(packageRegistrations);

                // Commit changes
                _packageRepository.CommitChanges();
                _packageDeletesRepository.CommitChanges();
                transaction.Commit();
            }
            EntitiesConfiguration.SuspendExecutionStrategy = false;


            // Force refresh the index
            UpdateSearchIndex();
        }
예제 #4
0
        public void AddPackageOwner(PackageRegistration package, User user)
        {
            package.Owners.Add(user);
            _packageRepository.CommitChanges();

            var request = FindExistingPackageOwnerRequest(package, user);

            if (request != null)
            {
                _packageOwnerRequestRepository.DeleteOnCommit(request);
                _packageOwnerRequestRepository.CommitChanges();
            }
        }
예제 #5
0
        public void DeletePackage(string id, string version, bool commitChanges = true)
        {
            var package = FindPackageByIdAndVersion(id, version);

            if (package == null)
            {
                throw new EntityException(Strings.PackageWithIdAndVersionNotFound, id, version);
            }

            var packageRegistration = package.PackageRegistration;

            _packageRepository.DeleteOnCommit(package);

            UpdateIsLatest(packageRegistration);

            if (packageRegistration.Packages.Count == 0)
            {
                _packageRegistrationRepository.DeleteOnCommit(packageRegistration);
            }

            if (commitChanges)
            {
                // we don't need to call _packageRegistrationRepository.CommitChanges() here because
                // it shares the same EntityContext as _packageRepository.
                _packageRepository.CommitChanges();

                NotifyIndexingService();
            }
        }
예제 #6
0
        public User AutoEnroll(string username, string password)
        {
            if (ValidateUser(username, password))
            {
                var searchResult = GetUserSearchResult(username, password);
                var user         = new User(GetStringProperty(searchResult, Properties.Username).ToLowerInvariant(), ".")
                {
                    ApiKey                = Guid.NewGuid(),
                    DisplayName           = GetStringProperty(searchResult, Properties.DisplayName),
                    PasswordHashAlgorithm = "LDAP"
                };
                var email = GetStringProperty(searchResult, Properties.Email);
                if (!string.IsNullOrEmpty(email))
                {
                    user.EmailAllowed            = true;
                    user.UnconfirmedEmailAddress = email.ToLowerInvariant();
                    user.EmailConfirmationToken  = cryptoSvc.GenerateToken();
                    user.ConfirmEmailAddress();
                }
                userRepo.InsertOnCommit(user);
                userRepo.CommitChanges();

                return(user);
            }
            return(null);
        }
예제 #7
0
 public void AddDownloadStatistics(PackageStatistics stats)
 {
     // IMPORTANT: Until we understand privacy implications of storing IP Addresses thoroughly,
     // It's better to just not store them. Hence "unknown". - Phil Haack 10/6/2011
     stats.IPAddress = "unknown";
     _packageStatsRepository.InsertOnCommit(stats);
     _packageStatsRepository.CommitChanges();
 }
        public void SaveCourseAchievements(User user, UserCourseAchievement achievement, int courseModuleKey)
        {
            var existingAchievements = GetUserCourseAchievements(user).AsQueryable();

            CompareAndPrepareCourseAchievement(achievement, courseModuleKey, user, existingAchievements);

            _courseCourseAchievementRepository.CommitChanges();
        }
예제 #9
0
        public void DeletePackage(string id, string version)
        {
            var package = FindPackageByIdAndVersion(id, version);

            if (package == null)
            {
                throw new EntityException(Strings.PackageWithIdAndVersionNotFound, id, version);
            }

            using (var tx = new TransactionScope())
            {
                var packageRegistration = package.PackageRegistration;
                packageRepo.DeleteOnCommit(package);
                packageFileSvc.DeletePackageFile(id, version);
                UpdateIsLatest(packageRegistration);
                packageRepo.CommitChanges();
                if (packageRegistration.Packages.Count == 0)
                {
                    packageRegistrationRepo.DeleteOnCommit(packageRegistration);
                    packageRegistrationRepo.CommitChanges();
                }
                tx.Complete();
            }

            NotifyIndexingService();
        }
        public void SaveProfiles(User user, EditProfileViewModel profile)
        {
            var siteProfiles = GetUserProfiles(user).AsQueryable();

            CompareAndPrepareProfile(
                SiteProfileConstants.Blog,
                profile.BlogUrl,
                user.Username,
                string.Empty,
                siteProfiles,
                prefix: string.Empty);
            CompareAndPrepareProfile(
                SiteProfileConstants.Github,
                profile.GithubUserName,
                user.Username,
                SiteProfileConstants.Images.github,
                siteProfiles,
                prefix: SiteProfileConstants.GithubProfilePrefix);
            CompareAndPrepareProfile(
                SiteProfileConstants.Homepage,
                profile.HomepageUrl,
                user.Username,
                string.Empty,
                siteProfiles,
                prefix: string.Empty);
            CompareAndPrepareProfile(
                SiteProfileConstants.StackExchange,
                profile.StackExchangeUrl,
                user.Username,
                SiteProfileConstants.Images.stackexchange,
                siteProfiles,
                prefix: string.Empty);
            CompareAndPrepareProfile(
                SiteProfileConstants.Twitter,
                profile.TwitterUserName,
                user.Username,
                SiteProfileConstants.Images.twitter,
                siteProfiles,
                prefix: SiteProfileConstants.TwitterProfilePrefix);
            CompareAndPrepareProfile(
                SiteProfileConstants.PackagesRepository,
                profile.PackagesRepository,
                user.Username,
                string.Empty,
                siteProfiles,
                prefix: string.Empty);
            CompareAndPrepareProfile(
                SiteProfileConstants.PackagesRepositoryAuto,
                profile.PackagesRepositoryAuto,
                user.Username,
                string.Empty,
                siteProfiles,
                prefix: string.Empty);

            profileRepo.CommitChanges();
        }
예제 #11
0
        public void SaveOrUpdateResults(PackageScanResult result, Package package)
        {
            var scanResult = _scanRepository.GetAll()
                             .Include(pr => pr.Packages)
                             .SingleOrDefault(s => s.Sha256Checksum == result.Sha256Checksum);

            if (scanResult == null)
            {
                scanResult = new ScanResult();
                _scanRepository.InsertOnCommit(scanResult);
            }

            scanResult.Sha256Checksum = result.Sha256Checksum.to_string();
            scanResult.FileName       = result.FileName.to_string();
            scanResult.ScanData       = result.ScanData.to_string();
            scanResult.ScanDetailsUrl = result.ScanDetailsUrl.to_string();

            int positives = 0;

            int.TryParse(result.Positives.to_string(), out positives);
            scanResult.Positives = positives;

            int totalScans = 0;

            int.TryParse(result.TotalScans.to_string(), out totalScans);
            scanResult.TotalScans = totalScans;

            var scanDate = DateTime.MinValue;

            DateTime.TryParse(result.ScanDate.to_string(), out scanDate);
            if (scanDate != DateTime.MinValue)
            {
                scanResult.ScanDate = scanDate;
            }

            var packageLinked = false;

            foreach (var existingPackage in scanResult.Packages.OrEmptyListIfNull())
            {
                if (package.Key == existingPackage.Key)
                {
                    packageLinked = true;
                }
            }

            if (!packageLinked)
            {
                scanResult.Packages.Add(package);
            }

            _scanRepository.CommitChanges();
        }
        public void RecordPackageDownloadStatistics(int packageKey, string userHostAddress, string userAgent)
        {
            _packageStatsRepository.InsertOnCommit(
                new PackageStatistics
            {
                // IMPORTANT: Timestamp is managed by the database.
                IPAddress  = userHostAddress,
                UserAgent  = userAgent,
                PackageKey = packageKey
            });

            _packageStatsRepository.CommitChanges();
        }
예제 #13
0
        public void PublishPackage(Package package, bool commitChanges = true)
        {
            if (package == null)
            {
                throw new ArgumentNullException(nameof(package));
            }

            package.Published = DateTime.UtcNow;
            package.Listed    = true;

            UpdateIsLatest(package.PackageRegistration, false);

            if (commitChanges)
            {
                _packageRepository.CommitChanges();
            }
        }
예제 #14
0
        public virtual User Create(
            string username,
            string password,
            string emailAddress)
        {
            // TODO: validate input
            // TODO: consider encrypting email address with a public key, and having the background process that send messages have the private key to decrypt

            var existingUser = FindByUsername(username);

            if (existingUser != null)
            {
                throw new EntityException(Strings.UsernameNotAvailable, username);
            }

            existingUser = FindByEmailAddress(emailAddress);
            if (existingUser != null)
            {
                throw new EntityException(Strings.EmailAddressBeingUsed, emailAddress);
            }

            var hashedPassword = cryptoSvc.GenerateSaltedHash(password, Constants.PBKDF2HashAlgorithmId);

            var newUser = new User(
                username,
                hashedPassword)
            {
                ApiKey       = Guid.NewGuid(),
                EmailAllowed = true,
                EmailAllModerationNotifications = true,
                UnconfirmedEmailAddress         = emailAddress,
                EmailConfirmationToken          = cryptoSvc.GenerateToken(),
                PasswordHashAlgorithm           = Constants.PBKDF2HashAlgorithmId,
            };

            if (!config.ConfirmEmailAddresses)
            {
                newUser.ConfirmEmailAddress();
            }

            userRepo.InsertOnCommit(newUser);
            userRepo.CommitChanges();

            return(newUser);
        }
예제 #15
0
        public void AddDownloadStatistics(Package package, string userHostAddress, string userAgent, string operation)
        {
            _packageStatsRepository.InsertOnCommit(
                new PackageStatistics
            {
                // IMPORTANT: Timestamp is managed by the database.

                // IMPORTANT: Until we understand privacy implications of storing IP Addresses thoroughly,
                // It's better to just not store them. Hence "unknown". - Phil Haack 10/6/2011
                IPAddress = "unknown",
                UserAgent = userAgent,
                Package   = package,
                Operation = operation
            });

            _packageStatsRepository.CommitChanges();
        }
예제 #16
0
        public void AddDownloadStatistics(Package package, string userHostAddress, string userAgent)
        {
            using (MiniProfiler.Current.Step("Updating package stats"))
            {
                packageStatsRepo.InsertOnCommit(new PackageStatistics
                {
                    // IMPORTANT: Timestamp is managed by the database.

                    // IMPORTANT: Until we understand privacy implications of storing IP Addresses thoroughly,
                    // It's better to just not store them. Hence "unknown". - Phil Haack 10/6/2011
                    IPAddress = "unknown",
                    UserAgent = userAgent,
                    Package   = package
                });

                packageStatsRepo.CommitChanges();
            }
        }
예제 #17
0
        public Package CreatePackage(INupkg nugetPackage, User user, bool commitChanges = true)
        {
            ValidateNuGetPackageMetadata(nugetPackage.Metadata);

            var packageRegistration = CreateOrGetPackageRegistration(user, nugetPackage.Metadata);

            var package = CreatePackageFromNuGetPackage(packageRegistration, nugetPackage, user);

            packageRegistration.Packages.Add(package);
            UpdateIsLatest(packageRegistration);

            if (commitChanges)
            {
                _packageRegistrationRepository.CommitChanges();
                NotifyIndexingService();
            }

            return(package);
        }
예제 #18
0
        public Package CreatePackage(PackageReader nugetPackage, PackageStreamMetadata packageStreamMetadata, User user, bool commitChanges = true)
        {
            var packageMetadata = PackageMetadata.FromNuspecReader(nugetPackage.GetNuspecReader());

            ValidateNuGetPackageMetadata(packageMetadata);

            var packageRegistration = CreateOrGetPackageRegistration(user, packageMetadata);

            var package = CreatePackageFromNuGetPackage(packageRegistration, nugetPackage, packageMetadata, packageStreamMetadata, user);

            packageRegistration.Packages.Add(package);
            UpdateIsLatest(packageRegistration, false);

            if (commitChanges)
            {
                _packageRegistrationRepository.CommitChanges();
                NotifyIndexingService();
            }

            return(package);
        }
예제 #19
0
        Package CreatePackageFromNuGetPackage(PackageRegistration packageRegistration, IPackage nugetPackage)
        {
            var package = packageRegistration.Packages
                          .Where(pv => pv.Version == nugetPackage.Version.ToString())
                          .SingleOrDefault();

            if (package != null)
            {
                switch (package.Status)
                {
                case PackageStatusType.Rejected:
                    throw new EntityException(string.Format("This package has been {0} and can no longer be submitted.", package.Status.GetDescriptionOrValue().ToLower()));

                case PackageStatusType.Submitted:
                    //continue on
                    break;

                default:
                    throw new EntityException("A package with identifier '{0}' and version '{1}' already exists.", packageRegistration.Id, package.Version);
                }
            }

            var now = DateTime.UtcNow;
            var packageFileStream = nugetPackage.GetStream();

            //if new package versus updating an existing package.
            if (package == null)
            {
                package = new Package();
            }

            package.Version      = nugetPackage.Version.ToString();
            package.Description  = nugetPackage.Description;
            package.ReleaseNotes = nugetPackage.ReleaseNotes;
            package.RequiresLicenseAcceptance = nugetPackage.RequireLicenseAcceptance;
            package.HashAlgorithm             = Constants.Sha512HashAlgorithmId;
            package.Hash            = cryptoSvc.GenerateHash(packageFileStream.ReadAllBytes());
            package.PackageFileSize = packageFileStream.Length;
            package.Created         = now;
            package.Language        = nugetPackage.Language;
            package.LastUpdated     = now;
            package.Published       = now;
            package.Copyright       = nugetPackage.Copyright;
            package.IsPrerelease    = !nugetPackage.IsReleaseVersion();
            package.Listed          = false;
            package.Status          = PackageStatusType.Submitted;
            package.SubmittedStatus = PackageSubmittedStatusType.Ready;
            package.ApprovedDate    = null;

            if (package.ReviewedDate.HasValue)
            {
                package.SubmittedStatus = PackageSubmittedStatusType.Updated;
            }

            //we don't moderate prereleases
            if (package.IsPrerelease)
            {
                package.Listed = true;
                package.Status = PackageStatusType.Exempted;
            }
            if (packageRegistration.IsTrusted)
            {
                package.Listed       = true;
                package.Status       = PackageStatusType.Approved;
                package.ReviewedDate = now;
                package.ApprovedDate = now;
            }

            package.IconUrl    = nugetPackage.IconUrl == null ? string.Empty : nugetPackage.IconUrl.ToString();
            package.LicenseUrl = nugetPackage.LicenseUrl == null ? string.Empty : nugetPackage.LicenseUrl.ToString();
            package.ProjectUrl = nugetPackage.ProjectUrl == null ? string.Empty : nugetPackage.ProjectUrl.ToString();
            package.Summary    = nugetPackage.Summary ?? string.Empty;
            package.Tags       = nugetPackage.Tags ?? string.Empty;
            package.Title      = nugetPackage.Title ?? string.Empty;

            foreach (var item in package.Authors.OrEmptyListIfNull().ToList())
            {
                packageAuthorRepo.DeleteOnCommit(item);
            }
            packageAuthorRepo.CommitChanges();
            foreach (var author in nugetPackage.Authors)
            {
                package.Authors.Add(new PackageAuthor {
                    Name = author
                });
            }

            foreach (var item in package.SupportedFrameworks.OrEmptyListIfNull().ToList())
            {
                packageFrameworksRepo.DeleteOnCommit(item);
            }
            packageFrameworksRepo.CommitChanges();
            var supportedFrameworks = GetSupportedFrameworks(nugetPackage).Select(fn => fn.ToShortNameOrNull()).ToArray();

            if (!supportedFrameworks.AnySafe(sf => sf == null))
            {
                foreach (var supportedFramework in supportedFrameworks)
                {
                    package.SupportedFrameworks.Add(new PackageFramework {
                        TargetFramework = supportedFramework
                    });
                }
            }

            foreach (var item in package.Dependencies.OrEmptyListIfNull().ToList())
            {
                packageDependenciesRepo.DeleteOnCommit(item);
            }
            packageDependenciesRepo.CommitChanges();
            foreach (var dependencySet in nugetPackage.DependencySets)
            {
                if (dependencySet.Dependencies.Count == 0)
                {
                    package.Dependencies.Add(new PackageDependency
                    {
                        Id              = null,
                        VersionSpec     = null,
                        TargetFramework = dependencySet.TargetFramework.ToShortNameOrNull()
                    });
                }
                else
                {
                    foreach (var dependency in dependencySet.Dependencies.Select(d => new { d.Id, d.VersionSpec, dependencySet.TargetFramework }))
                    {
                        package.Dependencies.Add(new PackageDependency
                        {
                            Id              = dependency.Id,
                            VersionSpec     = dependency.VersionSpec == null ? null : dependency.VersionSpec.ToString(),
                            TargetFramework = dependency.TargetFramework.ToShortNameOrNull()
                        });
                    }
                }
            }

            foreach (var item in package.Files.OrEmptyListIfNull().ToList())
            {
                packageFilesRepo.DeleteOnCommit(item);
            }
            packageFilesRepo.CommitChanges();
            foreach (var packageFile in nugetPackage.GetFiles().OrEmptyListIfNull())
            {
                var filePath    = packageFile.Path;
                var fileContent = " ";

                IList <string> extensions         = new List <string>();
                var            approvedExtensions = Configuration.ReadAppSettings("PackageFileTextExtensions");
                if (!string.IsNullOrWhiteSpace(approvedExtensions))
                {
                    foreach (var extension in approvedExtensions.Split(',', ';'))
                    {
                        extensions.Add("." + extension);
                    }
                }

                try
                {
                    var extension = Path.GetExtension(filePath);

                    if (extension != null)
                    {
                        if (extensions.Contains(extension))
                        {
                            fileContent = packageFile.GetStream().ReadToEnd();
                        }
                        else if (extension.Equals(".exe", StringComparison.InvariantCultureIgnoreCase))
                        {
                            var bytes    = packageFile.GetStream().ReadAllBytes();
                            var md5Hash  = BitConverter.ToString(Convert.FromBase64String(cryptoSvc.GenerateHash(bytes, "MD5"))).Replace("-", string.Empty);
                            var sha1Hash = BitConverter.ToString(Convert.FromBase64String(cryptoSvc.GenerateHash(bytes, "SHA1"))).Replace("-", string.Empty);

                            fileContent = string.Format("md5: {0} | sha1: {1}", md5Hash, sha1Hash);
                        }
                    }
                }
                catch (Exception ex)
                {
                    // Log but swallow the exception
                    Elmah.ErrorSignal.FromCurrentContext().Raise(ex);
                }

                package.Files.Add(new PackageFile
                {
                    FilePath    = filePath,
                    FileContent = fileContent,
                });
            }

            package.FlattenedAuthors      = package.Authors.Flatten();
            package.FlattenedDependencies = package.Dependencies.Flatten();

            return(package);
        }