Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
Merge pull request #3997 from NuGet/dev
[ReleasePrep][2017.05.19]RI of dev into master
  • Loading branch information
ryuyu committed May 22, 2017
2 parents 7a586a6 + 3ac8517 commit f8c9246
Show file tree
Hide file tree
Showing 91 changed files with 3,750 additions and 1,081 deletions.
2 changes: 1 addition & 1 deletion README.md
Expand Up @@ -17,7 +17,7 @@ This project has adopted the [Microsoft Open Source Code of Conduct](https://ope
2. PowerShell 4.0
2. Clone it!

```PS C:\Code> git clone git@github.com:NuGet/NuGetGallery.git```
```PS C:\Code> git clone https://github.com/NuGet/NuGetGallery.git```
3. Build it!

```
Expand Down
@@ -0,0 +1,22 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.

namespace NuGetGallery.Auditing.AuditedEntities
{
/// <summary>
/// Auditing details for UserSecurityPolicy entity.
/// </summary>
public class AuditedUserSecurityPolicy
{
public string Name { get; }
public string Subscription { get; }
public string Value { get; }

public AuditedUserSecurityPolicy(UserSecurityPolicy policy)
{
Name = policy.Name;
Subscription = policy.Subscription;
Value = policy.Value;
}
}
}
3 changes: 1 addition & 2 deletions src/NuGetGallery.Core/Auditing/AuditedPackageAction.cs
Expand Up @@ -12,7 +12,6 @@ public enum AuditedPackageAction
Unlist,
Edit,
UndoEdit,


Verify
}
}
11 changes: 11 additions & 0 deletions src/NuGetGallery.Core/Auditing/AuditedSecurityPolicyAction.cs
@@ -0,0 +1,11 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.

namespace NuGetGallery.Auditing
{
public enum AuditedSecurityPolicyAction
{
Create,
Verify
}
}
4 changes: 3 additions & 1 deletion src/NuGetGallery.Core/Auditing/AuditedUserAction.cs
Expand Up @@ -14,6 +14,8 @@ public enum AuditedUserAction
ChangeEmail,
CancelChangeEmail,
ConfirmEmail,
Login
Login,
SubscribeToPolicies,
UnsubscribeFromPolicies
}
}
16 changes: 0 additions & 16 deletions src/NuGetGallery.Core/Auditing/UserAuditAction.cs

This file was deleted.

19 changes: 18 additions & 1 deletion src/NuGetGallery.Core/Auditing/UserAuditRecord.cs
Expand Up @@ -4,6 +4,7 @@
using System;
using System.Collections.Generic;
using System.Linq;
using NuGetGallery.Auditing.AuditedEntities;

namespace NuGetGallery.Auditing
{
Expand All @@ -17,6 +18,11 @@ public class UserAuditRecord : AuditRecord<AuditedUserAction>
public CredentialAuditRecord[] AffectedCredential { get; }
public string AffectedEmailAddress { get; }

/// <summary>
/// Subset of user policies affected by the action (subscription / unsubscription).
/// </summary>
public AuditedUserSecurityPolicy[] AffectedPolicies { get; }

public UserAuditRecord(User user, AuditedUserAction action)
: this(user, action, Enumerable.Empty<Credential>())
{
Expand Down Expand Up @@ -55,7 +61,18 @@ public UserAuditRecord(User user, AuditedUserAction action, string affectedEmail
{
AffectedEmailAddress = affectedEmailAddress;
}


public UserAuditRecord(User user, AuditedUserAction action, IEnumerable<UserSecurityPolicy> affectedPolicies)
: this(user, action, Enumerable.Empty<Credential>())
{
if (affectedPolicies == null || affectedPolicies.Count() == 0)
{
throw new ArgumentException(nameof(affectedPolicies));
}

AffectedPolicies = affectedPolicies.Select(p => new AuditedUserSecurityPolicy(p)).ToArray();
}

public override string GetPath()
{
return Username.ToLowerInvariant();
Expand Down
50 changes: 50 additions & 0 deletions src/NuGetGallery.Core/Auditing/UserSecurityPolicyAuditRecord.cs
@@ -0,0 +1,50 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.

using System;
using System.Collections.Generic;
using System.Linq;
using NuGetGallery.Auditing.AuditedEntities;

namespace NuGetGallery.Auditing
{
/// <summary>
/// Audit record for user security policy evaluations.
/// </summary>
public class UserSecurityPolicyAuditRecord : AuditRecord<AuditedSecurityPolicyAction>
{
public string Username { get; }

public AuditedUserSecurityPolicy[] AffectedPolicies { get; }

public bool Success { get; set; }

public string ErrorMessage { get; }

public UserSecurityPolicyAuditRecord(string username,
AuditedSecurityPolicyAction action,
IEnumerable<UserSecurityPolicy> affectedPolicies,
bool success, string errorMessage = null)
:base(action)
{
if (string.IsNullOrEmpty(username))
{
throw new ArgumentNullException(nameof(username));
}
if (affectedPolicies == null || affectedPolicies.Count() == 0)
{
throw new ArgumentException(nameof(affectedPolicies));
}

Username = username;
AffectedPolicies = affectedPolicies.Select(p => new AuditedUserSecurityPolicy(p)).ToArray();
Success = success;
ErrorMessage = errorMessage;
}

public override string GetPath()
{
return Username.ToLowerInvariant();
}
}
}
1 change: 1 addition & 0 deletions src/NuGetGallery.Core/Entities/EntitiesContext.cs
Expand Up @@ -42,6 +42,7 @@ public EntitiesContext(string connectionString, bool readOnly)
public IDbSet<Credential> Credentials { get; set; }
public IDbSet<Scope> Scopes { get; set; }
public IDbSet<User> Users { get; set; }
public IDbSet<UserSecurityPolicy> UserSecurityPolicies { get; set; }

IDbSet<T> IEntitiesContext.Set<T>()
{
Expand Down
3 changes: 2 additions & 1 deletion src/NuGetGallery.Core/Entities/IEntitiesContext.cs
Expand Up @@ -13,8 +13,9 @@ public interface IEntitiesContext
IDbSet<PackageRegistration> PackageRegistrations { get; set; }
IDbSet<Credential> Credentials { get; set; }
IDbSet<Scope> Scopes { get; set; }

IDbSet<User> Users { get; set; }
IDbSet<UserSecurityPolicy> UserSecurityPolicies { get; set; }

Task<int> SaveChangesAsync();
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Naming", "CA1716:IdentifiersShouldNotMatchKeywords", MessageId = "Set", Justification="This is to match the EF terminology.")]
IDbSet<T> Set<T>() where T : class;
Expand Down
43 changes: 40 additions & 3 deletions src/NuGetGallery.Core/Entities/UserSecurityPolicy.cs
@@ -1,22 +1,30 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.

using System;
using System.ComponentModel.DataAnnotations;

namespace NuGetGallery
{
/// <summary>
/// User-subscribed security policy.
/// </summary>
public class UserSecurityPolicy : IEntity
public class UserSecurityPolicy : IEntity, IEquatable<UserSecurityPolicy>
{
public UserSecurityPolicy()
{
}

public UserSecurityPolicy(string name)
public UserSecurityPolicy(UserSecurityPolicy policy)
: this(policy.Name, policy.Subscription, policy.Value)
{
Name = name;
}

public UserSecurityPolicy(string name, string subscription, string value = null)
{
Name = name ?? throw new ArgumentNullException(nameof(name));
Subscription = subscription ?? throw new ArgumentNullException(nameof(subscription));
Value = value;
}

/// <summary>
Expand All @@ -38,11 +46,40 @@ public UserSecurityPolicy(string name)
/// Type name for the policy handler that provides policy behavior.
/// </summary>
[Required]
[StringLength(256)]
public string Name { get; set; }

/// <summary>
/// Name of subscription that added this policy.
/// </summary>
[Required]
[StringLength(256)]
public string Subscription { get; set; }

/// <summary>
/// Support for JSON-serialized properties for specific policies.
/// </summary>
public string Value { get; set; }

/// <summary>
/// Determine if two policies are equal.
/// </summary>
public bool Equals(UserSecurityPolicy other)
{
return Name.Equals(other.Name, StringComparison.OrdinalIgnoreCase) &&
Subscription.Equals(other.Subscription, StringComparison.OrdinalIgnoreCase) &&
(
(string.IsNullOrEmpty(Value) && string.IsNullOrEmpty(other.Value)) ||
(Value.Equals(other.Value, StringComparison.OrdinalIgnoreCase))
);
}

private static readonly Func<object, long, long> _hash = (i, hash) => ((hash << 5) + hash) ^ (i?.GetHashCode() ?? 0);
private const long _seed = 0x1505L;

public override int GetHashCode()
{
return _hash(Value, _hash(Subscription, _hash(Name, _seed))).GetHashCode();
}
}
}
4 changes: 3 additions & 1 deletion src/NuGetGallery.Core/NuGetGallery.Core.csproj
Expand Up @@ -122,11 +122,14 @@
<Compile Include="Auditing\AuditedEntities\AuditedPackage.cs" />
<Compile Include="Auditing\AuditedEntities\AuditedPackageIdentifier.cs" />
<Compile Include="Auditing\AuditedAuthenticatedOperationAction.cs" />
<Compile Include="Auditing\AuditedEntities\AuditedUserSecurityPolicy.cs" />
<Compile Include="Auditing\AuditedSecurityPolicyAction.cs" />
<Compile Include="Auditing\AuditEntry.cs" />
<Compile Include="Auditing\AuditActor.cs" />
<Compile Include="Auditing\AuditingService.cs" />
<Compile Include="Auditing\AuditRecord.cs" />
<Compile Include="Auditing\FailedAuthenticatedOperationAuditRecord.cs" />
<Compile Include="Auditing\UserSecurityPolicyAuditRecord.cs" />
<Compile Include="Auditing\FileSystemAuditingService.cs" />
<Compile Include="Auditing\CloudAuditingService.cs" />
<Compile Include="Auditing\CredentialAuditRecord.cs" />
Expand All @@ -139,7 +142,6 @@
<Compile Include="Auditing\AuditedUserAction.cs" />
<Compile Include="Auditing\PackageAuditRecord.cs" />
<Compile Include="Auditing\ScopeAuditRecord.cs" />
<Compile Include="Auditing\UserAuditAction.cs" />
<Compile Include="Auditing\UserAuditRecord.cs" />
<Compile Include="CoreConstants.cs" />
<Compile Include="CredentialTypes.cs" />
Expand Down
3 changes: 3 additions & 0 deletions src/NuGetGallery/App_Start/DefaultDependenciesModule.cs
Expand Up @@ -207,6 +207,9 @@ protected override void Load(ContainerBuilder builder)
.As<ISecurityPolicyService>()
.InstancePerLifetimeScope();

builder.RegisterType<SecurePushSubscription>()
.SingleInstance();

var mailSenderThunk = new Lazy<IMailSender>(
() =>
{
Expand Down
10 changes: 10 additions & 0 deletions src/NuGetGallery/App_Start/Routes.cs
Expand Up @@ -69,11 +69,21 @@ public static void RegisterUIRoutes(RouteCollection routes)
"stats/packages/{id}/{version}",
new { controller = "Statistics", action = "PackageDownloadsDetail" });

routes.MapRoute(
RouteName.StatisticsPackageDownloadsDetailReport,
"stats/reports/packages/{id}/{version}",
new { controller = "Statistics", action = "PackageDownloadsDetailReport" });

routes.MapRoute(
RouteName.StatisticsPackageDownloadsByVersion,
"stats/packages/{id}",
new { controller = "Statistics", action = "PackageDownloadsByVersion" });

routes.MapRoute(
RouteName.StatisticsPackageDownloadsByVersionReport,
"stats/reports/packages/{id}",
new { controller = "Statistics", action = "PackageDownloadsByVersionReport" });

routes.MapRoute(
RouteName.JsonApi,
"json/{action}",
Expand Down

0 comments on commit f8c9246

Please sign in to comment.