GithubHelp home page GithubHelp logo

microsoft / partner-center-dotnet-samples Goto Github PK

View Code? Open in Web Editor NEW
89.0 25.0 111.0 4.95 MB

Contains sample code on how to use the Partner Center .NET SDK

License: MIT License

C# 99.68% CSS 0.06% HTML 0.22% ASP.NET 0.01% Batchfile 0.02%
partnercenter csp sdk dotnet

partner-center-dotnet-samples's Introduction

Partner Center SDK for .NET Samples

This repository contains samples for the Partner Center SDK for .NET.

Samples List

Sample Name Description
SDK Samples Console application that demonstrates each scenario the Partner Center .NET SDK is capable of performing.
Secure App Model A set of projects that demonstrate how a Control Panel Vendor (CPV) and a Cloud Solution Provider (CSP) should implement the Secure App Model.

Reporting Security Issues

Security issues and bugs should be reported privately, via email, to the Microsoft Security Response Center (MSRC) at [email protected]. You should receive a response within 24 hours. If for some reason you do not, please follow up via email to ensure we received your original message. Further information, including the MSRC PGP key, can be found in the Security TechCenter.

partner-center-dotnet-samples's People

Contributors

adbhat-ms avatar alidhia avatar bmonticello avatar brijeshp-ms avatar cbarneyms avatar deepakku-work avatar dependabot[bot] avatar devblaster avatar gaurav-karna avatar harshabacharaju avatar idwilliams avatar jasongroce avatar jlaherran avatar jonahlytlemsft avatar kaminasy avatar kswartz6 avatar marksc-ms avatar microsoftopensource avatar msftgits avatar pradeepko avatar richard-mejia avatar riskrunner0 avatar romary349 avatar sankargopalan avatar shuaga avatar tamoms avatar thepill avatar trinadhryali avatar tylerbau avatar yulshmsft avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

partner-center-dotnet-samples's Issues

Assigning licenses to a user throws an error "License assignment cannot be done for user with invalid usage location."

Hi,

I've started getting the strange issue when using the standard assign licenses call from the Partner Center SDK:
_partnerOperations.Customers.ById(this._tenantId).Users.ById(userId).LicenseUpdates.Create(updateLicense);

The error returned is "License assignment cannot be done for user with invalid usage location."

But the user clearly has the usageLocation set which is visible in both Entra ID and Partner Center

This happens only for certain customers in the same Partner Center and using the same API.

This API has been working correctly for a long time and now suddenly, it causes issues

What else could be the issue here?

Any help would be appreciated

UPDATE: When using the Partner Center REST API (which is recommended), I get the same exact error !!

Make Microsoft.Store.PartnerCenter nuget source code available on a public repo

Feature Request

Is your feature request related to a problem? Please describe.
I spent a whole day discovering a bug related with a property (refundable quantities) in the latest version of the nuget package, and I needed to implement a workaround by calling directly the Partner Center API without using the nuget package. I would have solved this by doing a pull request on the public repository, as it is being done in almost all the Microsoft .NET projects and saved time to others having the same issue.

The nuget package is a wrapper of a well-document public API, so I don't understand the reason for not making publicly available.

Describe the solution you would like
Share the Microsoft.Store.PartnerCenter source code in a GitHub public repo

Describe alternatives you have considered
The alternative is not to use Microsoft's nuget package, and build my own wrapper of the API, but that would be against the latest Microsoft open sourcing spirit, right?

Microsoft Partner center APP + USER authentication using owin

We are working on Microsoft partner center APIs integration in our application. Here in Partner center SDK one example is given how we can apply app+user authentication to consume partner center apis. We want to know how we can integrate it with our asp.net core rest apis as well as Single page application (ReactJs).

Response status code does not indicate success: 401 (Unauthorized).

Deployed Script and used Live Credentials - get this after signing in with Global Admin with 2 different accounts. Permissions assigned in App Registrations in Azure are the ones which were setup automatically when I created Partner Center Web App.

Any help would be appreciated please.

image

Tool does not close properly

Steps to reproduce

Please choose an option:

  1. Fetch customer agreement records
  2. Update customer agreement records
  3. Exit

1
Enter a desired absolute path to an existing directory to read/write the agreement records.
Default directory [Enter to Accept]: C:\Users\Administrator\Desktop

Expected behavior.

A list of about 1000 rows is created.
Because my customers are about 1000 users

Actual behavior

A list of 25000000 rows was created.
Also, the tool stopped working in the middle of creation.

Diagnostic logs

2024-03-14 19:06:53.458 +09:00 [ERR] An API exception occurred with status code: "OK", Content: null, Correlation ID: 158f449c-aa82-4600-a101-5da9a8dba1f3, Request ID: 1ae526bf-ea28-43d4-bf8c-3698361e1ad1
Refit.ApiException: An error occured deserializing the response.
---> System.IO.IOException: Unable to read data from the transport connection: 既存の接続はリモート ホストに強制的に切断されました。.
---> System.Net.Sockets.SocketException (10054): 既存の接続はリモート ホストに強制的に切断されました。
--- End of inner exception stack trace ---
at System.Net.Sockets.Socket.AwaitableSocketAsyncEventArgs.ThrowException(SocketError error, CancellationToken cancellationToken)
at System.Net.Sockets.Socket.AwaitableSocketAsyncEventArgs.System.Threading.Tasks.Sources.IValueTaskSource<System.Int32>.GetResult(Int16 token)
at System.Net.Http.HttpConnection.ReadAsync(Memory1 destination) at System.Net.Http.HttpConnection.RawConnectionStream.ReadAsync(Memory1 buffer, CancellationToken cancellationToken)
at System.Runtime.CompilerServices.PoolingAsyncValueTaskMethodBuilder1.StateMachineBox1.System.Threading.Tasks.Sources.IValueTaskSource.GetResult(Int16 token)
at System.Net.Security.SslStream.EnsureFullTlsFrameAsync[TIOAdapter](CancellationToken cancellationToken, Int32 estimatedSize)
at System.Runtime.CompilerServices.PoolingAsyncValueTaskMethodBuilder1.StateMachineBox1.System.Threading.Tasks.Sources.IValueTaskSource.GetResult(Int16 token)
at System.Net.Security.SslStream.ReadAsyncInternal[TIOAdapter](Memory1 buffer, CancellationToken cancellationToken) at System.Runtime.CompilerServices.PoolingAsyncValueTaskMethodBuilder1.StateMachineBox1.System.Threading.Tasks.Sources.IValueTaskSource<TResult>.GetResult(Int16 token) at System.Net.Http.HttpConnection.FillAsync(Boolean async) at System.Net.Http.HttpConnection.ChunkedEncodingReadStream.ReadAsyncCore(Memory1 buffer, CancellationToken cancellationToken)
at System.Text.Json.Serialization.ReadBufferState.ReadFromStreamAsync(Stream utf8Json, CancellationToken cancellationToken, Boolean fillBuffer)
at System.Text.Json.Serialization.Metadata.JsonTypeInfo1.DeserializeAsync(Stream utf8Json, CancellationToken cancellationToken) at System.Net.Http.Json.HttpContentJsonExtensions.ReadFromJsonAsyncCore[T](HttpContent content, JsonSerializerOptions options, CancellationToken cancellationToken) at Refit.SystemTextJsonContentSerializer.FromHttpContentAsync[T](HttpContent content, CancellationToken cancellationToken) at Refit.RequestBuilderImplementation.DeserializeContentAsync[T](HttpResponseMessage resp, HttpContent content, CancellationToken cancellationToken) at Refit.RequestBuilderImplementation.<>c__DisplayClass14_02.<b__0>d.MoveNext()
--- End of inner exception stack trace ---
at Refit.RequestBuilderImplementation.<>c__DisplayClass14_0`2.<b__0>d.MoveNext() in /_/Refit/RequestBuilderImplementation.cs:line 298
--- End of stack trace from previous location ---
at MCARefreshBulkAttestationCLITool.Providers.CustomerProvider.FetchAndSaveCustomerAgreementRecords() in C:\Users\Administrator\Desktop\Partner-Center-DotNet-Samples-master\Partner-Center-DotNet-Samples-master\MCARefreshBulkAttestationCLITool\Providers\CustomerProvider.cs:line 68

NOT able to get Access Token

Steps to reproduce

Run CSP application with valid aap id, app secret and customer Id .
AuthenticationResult token = await serviceClient.RefreshAccessTokenAsync(
$"{AADInstance}/{tenantId}/oauth2/token",
"https://graph.microsoft.com",
refreshToken,
CSPApplicationId,
CSPApplicationSecret).ConfigureAwait(false);
.

Expected behavior

we are suppose to get valid token

Actual behavior

What is the behavior observed?

Diagnostic logs

Please share test platform diagnostics logs.
The logs may contain test assembly paths, kindly review and mask those before sharing.
CSPApplication.Exceptions.AuthenticationException: 'AADSTS65001: The user or administrator has not consented to use the application with ID '-----------' named 'partner center web app - ukb and app direct shared'. Send an interactive authorization request for this user and resource. Trace ID: ba83a30b-0515-44aa-a7f2-567913475d00 Correlation ID: d0ee1c19-1545-44ba-9f4d-8d91b4af0232 Timestamp: 2023-11-05 15:28:29Z'

Environment

Please share additional details about your environment.
windows 10 PC
Version

Forbidden

image

I tried running the sample SDK and it is authenticated but it said forbidden, I also have the partner consent working and the token is already on the KeyVault, anyone has the steps to fetch the token from KV in the console sample app?

AADInstance null in CSP and CPV examples

Overview

Samples don't work out of the box even when populating App.config with valid parameters

Reproduction

Create App Registration in a Patrner tenant using the following script:
https://gcits.com/knowledge-base/how-to-connect-to-delegated-office-365-tenants-using-the-secure-app-model/

Clone repo, plugin parameters returned from script into App.config

Expected Behavior

The application should not throw an except

Actual Behavior

Exception is thrown because AADInstance variable is null

Possible solutions

Change the following lines from

private static readonly string AADInstance = ConfigurationManager.AppSettings["AADInstance"];

to
private static readonly string AADInstance = ConfigurationManager.AppSettings["ida:AADInstance"];

private static readonly string AADInstance = ConfigurationManager.AppSettings["AADInstance"];

private static readonly string AADInstance = ConfigurationManager.AppSettings["AADInstance"];

AADSTS50011: No reply address is registered for the application.

I'm looking at the SDK samples with new changes you made for secure model. In LoginUserToAad a popup appears for user credentials. But when I'm done with the sign on, I've this message:

AADSTS50011: No reply address is registered for the application.

From the manifest file of the registered app I use requiredResourceAccess[0].resourceAccess[0].id as the ApplicationId. The application type to native (it's a not scheduled WPF application my alternative for #7).

Getting subscribedSku's throws an error "Tenant address information is not available"

Hello,

This issue started happening a couple of days ago for one on the tenants in the Partner Center API.

I'm using the standard call like in the image below:
var customerUserSubscribedSkus = _partnerOperations.Customers.ById(tenantId).SubscribedSkus.Get();
I'm passing the correct "tenantId" here

And getting the exception:
image

I can't seem to find this error anywhere
"Tenant address information is not available"

I'm using this package to work with Partner Center
image

The strange thing is that the same exact API works for many other Customers (passing the other tenantId) in Partner Center.
Even stranger is the fact that it sometimes does not throw this exception, it's totally random during the day.

Any help would be appreciated here :-)

Requested value 'Disabled' was not found

Steps to reproduce

When using the Microsoft.Store.PartnerCenter nuget package latest version (3.0.1), an exception occurs on deserialization when listing the subscriptions. This suddently started to happen today, July 18th, with no code changes on client side.

Expected behavior

Obtaining the list of subscriptions with no errors.

Actual behavior

An exception is thrown on deserialization, details below:
image

PLEASE, Make Microsoft.Store.PartnerCenter nuget source code available on a public repo as commented on #92

Documentation for using these samples

Feature Request

Provide setup walk through for both Azure Portal and CSP dashboard with screenshots.

Describe the solution you would like
Microsoft recently modified the way App Registrations work and the current documentation doesn't correlate with the current way of registering the app in the Azure Portal and the CSP dashboard.

Having a detailed walk through with screenshots of both the Azure Portal registration and the CSP Dashboard registration would be very beneficial. The screenshots should provide the exact values that are needed in the configuration for everything to work correctly.

So far I have spent many hours trying to get both the Native App and Web App registrations setup correctly without success. Assume the person who downloaded this sample knows nothing about the Azure App Registration and the CSP Dashboard app registration processes.

Also include creating the Azure Key Vault and provide screenshots of where the setting values come from.

Thank you.

Please add "Tags" property to "Customer" entity

Feature Request

Please add customer tags which were introduced in 2022-12 to Customer item.

var customerOperations = partnerOperations.Customers.ById(customerId);
customerItem = await customerOperations.GetAsync().ConfigureAwait(false);

customerItem has no Tags property.

CPV Sample - Refresh token malformed

Steps to reproduce

  1. Perform the partner consent and store the refresh token using Azure Key Vault
  2. Run the CPVSample project

Expected behavior

The sample project should obtain the refresh token and perform the request successfully.

Actual behavior

"error":"invalid_grant",
"error_description":"AADSTS70000: Transmission data parser failure: Refresh Token is malformed or invalid.\r\nTrace ID: 745a44cc-ff7a-4b4c-a395-b0f1d8c51900\r\nCorrelation ID: \r\nTimestamp: 2018-12-11 06:28:50Z",
"error_codes":[70000],
"timestamp":"2018-12-11 06:28:50Z",
"trace_id":"",
"correlation_id":""

References

This issue was raised on Yammer. The original report can be found here

Could not deserialize response

Steps to reproduce

What steps can reproduce the defect?
Please share the setup, sample project, version of Java etc.

Expected behavior

Share the expected output

Actual behavior

What is the behavior observed?

Diagnostic logs

Please share test platform diagnostics logs.
The logs may contain test assembly paths, kindly review and mask those before sharing.

Environment

Please share additional details about your environment.
Version

403-Forbidden response after successful login

I cloned this repo & installed all the required tools. Afterwards I build the project without any problems. I have chosen option 1 to export all customers. After logging in in my browser, the website said something like: successfull login, you can close the tab. But a System.Net.Http.HttpRequestException: 'Response status code does not indicate success: 403 (Forbidden).' was thrown. The (sandbox-) account I am using has all the peremissions needed for this action.

I am using Visual Studio 2022 and .NET 6

The detailed error message is:
System.Net.Http.HttpRequestException HResult=0x80131500 Message=Response status code does not indicate success: 403 (Forbidden). Source=System.Net.Http StackTrace: at System.Net.Http.HttpResponseMessage.EnsureSuccessStatusCode() at NCEBulkMigrationTool.CustomerProvider.<ExportCustomersAsync>d__2.MoveNext() in C:\Users\bst\Documents\projects\Partner-Center-Tool\NCEBulkMigrationTool\CustomerProvider.cs:line 81 at Program.<<<Main>$>g__RunAsync|0_1>d.MoveNext() in C:\Users\bst\Documents\projects\Partner-Center-Tool\NCEBulkMigrationTool\Program.cs:line 98 at Program.<<Main>$>d__0.MoveNext() in C:\Users\bst\Documents\projects\Partner-Center-Tool\NCEBulkMigrationTool\Program.cs:line 60

Partner Center API new NCE Subscription Issues

Steps to reproduce

What steps can reproduce the defect?

We have gone into the partner portal and given our client Example 10 E3 Licenses on a yearly term for their full-time employees. They have periods in the year where they have temps for a few months so they also acquire 5 NCE E3 Monthly termed licenses and are willing to pay the increased fee associated with being on a monthly term since the temps will not be there permanently.

The client Fires one of the full-time employees, and one of the temps. There is now an E3 yearly and E3 Monthly sitting in their available pool of licenses. We integrated an automation tool for provisioning and allocating licenses to users. Lets say they replace their full time employee, we want to pull the available yearly license, so that when the monthly comes up for renewal period in short order we can reduce it.

The problem is that the portal nor the API provide the term of the subscription. it just consolidated them into a total of 2 available to be allocated. HOW do we allocate the yearly termed license?

Expected behavior

I would expect that we can choose the appropriate license from the pool and allocate it so that we don't start renewing the new full time employee on a higher cost monthly termed license that could otherwise be reduced while the longer-term annual license could recognize full use.

Share the expected output

Actual behavior

No term is returned, it's just a total and we don't get to choose.

Authentication failed. MFA required. (10001)

Partner Exception:
Error Category: Unauthorized
Service Error Payload: null
Context: Request Id: f604e6a0-96be-4c53-bc57-b877e672ca77, Correlation Id: 71bb26c8-89f4-474d-882d-e35ac853283e, Locale: en-US
Base Description: Microsoft.Store.PartnerCenter.Exceptions.PartnerException: Authentication failed. MFA required. (10001)
at Microsoft.Store.PartnerCenter.PartnerService.SynchronousExecute[T](Func`1 operation)
at Microsoft.Store.PartnerCenter.Samples.Customers.GetPagedCustomers.RunScenario() in C:\sdk\SdkSamples\Customers\GetPagedCustomers.cs:line 42
at Microsoft.Store.PartnerCenter.Samples.BasePartnerScenario.Run() in C:\sdk\SdkSamples\BasePartnerScenario.cs:line 78

Bulk migration tool - System.ArgumentOutOfRangeException when exporting failed customers

Steps to reproduce

In bulk migration tool, select "2. Export subscriptions with migration eligibility".
Issue occurs after "Exporting failed customers" starts.

Expected behavior

Failed customer list is exported to CSV.

Actual behavior

Program crashes with "Unhandled exception. System.ArgumentOutOfRangeException".

Diagnostic logs

Unhandled exception. System.ArgumentOutOfRangeException: Length cannot be less than zero. (Parameter 'length')
   at System.String.Substring(Int32 startIndex, Int32 length)
   at NCEBulkMigrationTool.CsvProvider.ExportCsv[T](IEnumerable`1 data, String fileName) in C:\...\nce-bulk-migration-tool\NCEBulkMigrationTool\CsvProvider.cs:line 24
   at NCEBulkMigrationTool.SubscriptionProvider.ExportLegacySubscriptionsAsync() in C:\...\nce-bulk-migration-tool\NCEBulkMigrationTool\SubscriptionProvider.cs:line 79
   at Program.<<Main>$>g__RunAsync|0_1(IServiceProvider serviceProvider) in C:\...\nce-bulk-migration-tool\NCEBulkMigrationTool\Program.cs:line 85
   at Program.<Main>$(String[] args) in C:\...\nce-bulk-migration-tool\NCEBulkMigrationTool\Program.cs:line 54
   at Program.<Main>(String[] args)

Note the failing code in ExportCsv:

    int index = fileName.LastIndexOf('/');
    var directory = fileName[..index];  // fails here
    Directory.CreateDirectory(directory);

And the calling line from SubscriptionProvider.cs:

    if (failedCustomersBag.Count > 0)
    {
        Console.WriteLine("Exporting failed customers");
        await csvProvider.ExportCsv(failedCustomersBag, "failedCustomers.csv"); // calling line
        Console.WriteLine($"Exported failed customers at {Environment.CurrentDirectory}/failedCustomers.csv");
    }

The method is clearly being called with a filename only, so the attempt to locate the training slash returns a -1, causing the substring call to fail. The call should contain a folder path.

Environment

Using the latest posted code for the bulk migration tool.

Secure App Model - CSP Sample

Steps to reproduce

Retrieve an access token from Azure AD using the method in the CSP sample application for the secure app model. The expires on time is calculated incorrectly.

Expected behavior

The token should be valid for one hour.

Actual behavior

The token is only valid for a few minutes.

Diagnostic logs

Currently the code is
return new Tuple<string, DateTimeOffset>(token["access_token"].ToString(), DateTimeOffset.UtcNow + TimeSpan.FromTicks(long.Parse(token["expires_on"].ToString())));

It should look something similar to the following
return new Tuple<string, DateTimeOffset>(token["access_token"].ToString(), DateTimeOffset.FromUnixTimeSeconds(long.Parse(token["expires_on"].ToString())));

Access to exchange online from partner center

Are there any samples to accessing Exchange online from partner center?

What i want to be able to do is get a list of all mailboxes and shared mailboxes for a given client. I've looked at the examples/api reference and couldn't find anything that does this.

Ive seen examples in the powershell module that lets you do this here however this is not documented for the rest api.

Support of .Net 5

As you know that the ".Net 5" had been released on November 10th, 2020, I would like to know whether the official Microsoft.Store.PartnerCenter SDK supports ".Net 5" or not? Has anyone already tried this? Is there a Github repository for this SDK?

Mentioning you @IsaiahWilliams here, as you closed this issue.

Duplicated "PartnerMpnId" key in App.config

Steps to reproduce

Try to run the sample "GetSuscriptionsByMpnId" or "VerifyPartnerMpnId" having filled "PartnerMpnId" key in App.config

Expected behavior

Use the "PartnerMpnId" configured in App.config

Actual behavior

The application asks you to enter the MPN ID manually

Diagnostic logs

No logs but have seen the key is duplicated in app.config file

Environment

Development

clientId and clientSecret aren't used

Steps to reproduce

Set clientId and clientSecret to null inside GetAADTokenFromRefreshToken

Expected behavior

Authentication error

Actual behavior

We receive the accessToken correctly

Environment

PC SDK Version 1.10.0

Thoughts

I'm pretty sure that's not an actual issue, because we get the refresh_token via the clientId and clientSecret anyway. However the sample is pretty misleading and could be simplified by omitting these params, shortening the payload & method signature.

Not able fetch refresh token

Steps to reproduce

we have set all the information about the ad profile such as CSPAplication Id ,CSPApplicationSecret. when we try to login after set up values, it throw error for secret are not found at time of SetSecretAsync call. we try to run partner consent application to set refreshed token in key vault. we are using app only authentication in one of the tenants of our domains.
Notfound

What steps can reproduce the defect?

  1. Asp.net core 3.1 C#
  2. region Assembly Microsoft.Azure.KeyVault, Version=3.0.4.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35
  3. Method signature
    public static Task SetSecretAsync(this IKeyVaultClient operations, string vaultBaseUrl, string secretName, string value, IDictionary<string, string> tags = null, string contentType = null, SecretAttributes secretAttributes = null, CancellationToken cancellationToken = default);

Expected behavior

we get a refresh token for the defined user of azure portal for for given app managed key and corelated app registration client Id successfully.

Share the expected output

Actual behavior

please find the attached screen shot not found as above.

What is the behavior observed?

Diagnostic logs

at Microsoft.Azure.KeyVault.KeyVaultClient.d__66.MoveNext()
at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at System.Runtime.CompilerServices.ConfiguredTaskAwaitable1.ConfiguredTaskAwaiter.GetResult() at Microsoft.Azure.KeyVault.KeyVaultClientExtensions.<GetSecretAsync>d__12.MoveNext() at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw() at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task) at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task) at System.Runtime.CompilerServices.TaskAwaiter1.GetResult()
at Application.Services.KeyVaultProvider.d__11.MoveNext() in D:\Projects\ClientApp\Src\Services\Application\Services\KeyVaultProvider.cs:line 51

Environment

azure cloud
visual studio IDE

Non interactive user auth

Feature Request

Maybe I have missunderstand the SecureAppModel and what I looking for is already existing. The year before, when MFA was not mandatory, I could use User Auth by directly getting access token with user credential like this :

"Authentication": {
        "ApplicationId": "mypartnercenterappid",
        "ApplicationSecret": "mypartnercenterappsecret", 
        "ApplicationDomain": "xxxxxxxxx.onmicrosoft.com",
        "User": "[email protected]",
        "Password": "myuserpassword",
        "TenantId": "tenant of my organization",
        "Authority": "https://login.windows.net",
        "ResourceUrl": "https://graph.windows.net",
        "PartnerServiceApiRoot": "https://api.partnercenter.microsoft.com"
      }
        public async Task<IPartner> GetPartnerConnection()
        {
            if (_aggregatePartner != null && !_aggregatePartner.Credentials.IsExpired())
                return _aggregatePartner;
            PartnerService.Instance.ApiRootUrl = Configurations.Authentication.PartnerServiceApiRoot;

            IPartnerCredentials partnerCredentials = await PartnerCredentials.Instance.GenerateByUserCredentialsAsync(Configurations.Authentication.ApplicationId, await GetUserToken());
            _aggregatePartner = PartnerService.Instance.CreatePartnerOperations(partnerCredentials);
            
            return _aggregatePartner;
        }

        private async Task<AuthenticationToken> GetUserToken()
        {
            HttpResponseMessage response = await _client.PostAsync($"{Configurations.Authentication.Authority}/{Configurations.Authentication.TenantId}/oauth2/token", new FormUrlEncodedContent(new Dictionary<string, string>
            {
                { "scope", "openid" },
                { "grant_type", "password" },
                { "resource", Configurations.Authentication.PartnerServiceApiRoot },
                { "client_id", Configurations.Authentication.ApplicationId },
                { "client_secret", Configurations.Authentication.ApplicationSecret },
                { "username", Configurations.Authentication.User },
                { "password", Configurations.Authentication.Password }
            }));
            if (!response.IsSuccessStatusCode)
                throw new Exception($"Can't get partner center token for user \"{Configurations.Authentication.User}\"");
            JObject auth = JsonConvert.DeserializeObject<JObject>(await response.Content.ReadAsStringAsync());
            string accessToken = auth["access_token"].Value<string>();
            long expiresOn = auth["expires_on"].Value<long>();
            return new AuthenticationToken(accessToken, new DateTime(1970, 1, 1, 0, 0, 0, 0, DateTimeKind.Utc).AddSeconds(expiresOn).ToLocalTime());
        }

It was so simple, now, since arround october I can't use my GetUserToken function because response.IsSuccessStatusCode is false.

My application is an API that allow our customer's users to do actions on partner centers like : listing there users account and add/remove licence on user account.
For this, application auth is not sufficient, so I have to use User Auth. I want to use a service account that auto-login in background as before. Is there any solution ?

AADSTS65001: The user or administrator has not consented to use the application with ID 'Redacted' named 'Redacted'. Send an interactive authorization request for this user and resource.

Steps to reproduce

What steps can reproduce the defect?
Please share the setup, sample project, version of Java etc.

Use sample project proved here and attempt to get access token with refresh token for a partners tenant for graph api resource

Expected behavior

Get valid access token from refresh token

Actual behavior

Get exception with
AADSTS65001: The user or administrator has not consented to use the application with ID 'Redacted' named 'Redacted'. Send an interactive authorization request for this user and resource.

We have a multi-tenant application integrated with partner center api using this sample project as a base.

  • Using our internal Partner account access to all resources, Partner Center REST API and Graph API for our tenants functions correctly.
  • when we have an external partner authenticate we are able to get access to Partner Center REST API but are not able to get access to Graph API for the external Partners tenants.

v1 token endpoint response

AADSTS65001: The user or administrator has not consented to use the application with ID 'Redacted' named 'Redacted'. Send an interactive authorization request for this user and resource.
Trace ID: 8e074af4-1add-475c-bcfa-1c55c38a2000
Correlation ID: cd72c62e-a948-4a47-ac8a-aa05c6660886
Timestamp: 2020-05-13 12:41:00Z

v2 token endpoint response

AADSTS65001: The user or administrator has not consented to use the application with ID 'Redacted' named 'Redacted'. Send an interactive authorization request for this user and resource.
Trace ID: 45d93fe4-bafb-405a-a3d2-b69085ba2000
Correlation ID: 5514656d-d4b9-4327-a60f-6c4b1c1248f2
Timestamp: 2020-05-13 12:24:59Z

Acquire customer byId throws exception if Azure AD Graph (deprecated) permissions are removed

Steps to reproduce

Use appOnly context by using the PartnerCenter WebApp application registration
Backup Application Registration manifest.json from Azure Portal because that's the easiest way to return removed permissions
Replace Azure Active Directory Graph (as its deprecated long time ago) permissions for the application registration in Azure Portal with the equivalent Microsoft Graph permissions
(to be specific it is about Directory.Read.All)
After obtaining appOnly context in your c# code - call

Customer customer = await aggregatePartner.Customers.ById(tenantId).GetAsync();

Expected behavior

The SDK should return the details about the customer and fill the variable with the correct model data

Actual behavior

The PartnerException from sdk is invoked due to 403 response from the server. I assume that SDK is accessing some old endpoint/action because the same permissions are enough (Microsoft Graph - Directory.Read.All) if we are using REST api call equivalent with postman.

Diagnostic logs

Microsoft.Store.PartnerCenter.Exceptions.PartnerException
HResult=0x80131500
Message=The server returned error code '403' (Forbidden).
Source=Microsoft.Store.PartnerCenter
StackTrace:
at Microsoft.Store.PartnerCenter.Network.PartnerServiceProxy'2.d__70.MoveNext()
at Microsoft.Store.PartnerCenter.Network.PartnerServiceProxy'2.d__68.MoveNext()
at Microsoft.Store.PartnerCenter.Network.PartnerServiceProxy'2.d__58.MoveNext()
at Microsoft.Store.PartnerCenter.Customers.CustomerOperations.d__86.MoveNext()
at ....

Environment

.NET 6
Both Azure Functions and Windows11 - local development
All v3 versions of nuget, even the latest (3.4.0 at the moment)

Get usage data for subscription by meter return "Unknown error"

Partner.Center.SDK (15.1)

when try to get azrue resource usage for my customer the response after some times is
"Unknown error".

the full request:
var usageRecords = ApplicationDomain.Instance.PartnerCenterClient
.Customers
.ById(tenantId)
.Subscriptions
.ById(subId)
.UsageRecords
.ByMeter
.Get();

Rate card sample returns exception

Steps to reproduce

Expected behavior

  • Get Azure Rate Card details for the CSP

Actual behavior

  • Return an exception after successfully authenticating as shown in the screenshot below
    Screenshot_2

Diagnostic logs

Partner Exception:
Error Category: Forbidden
Service Error Payload: null
Context: Request Id: 50bf925d-c80e-4bcc-bb3f-214dab9cb7a0, Correlation Id: 1c9dca8f-64a7-4928-ad22-716481212030, Locale: en-US
Base Description: Microsoft.Store.PartnerCenter.Exceptions.PartnerException: {"message":"The supplied role does not have the rights to perform the requested operation."}

Additional Info

  • I have developer role for the partner center I am trying this on.
  • Please advise if something else needs to be verified or checked.
  • Please advise if there is an another alternative to fetch the CSP rate card.
  • The goal is to do this via a REST API call, tried the SDK sample to validate how it works, please recommend if anything else should be done for the REST API rate card calls for the CSP.

Error when getting Azure subscription utilization

Steps to reproduce

sample GetAzureSubscriptionUtilization

Expected behavior

it just works

Actual behavior

{
    "ErrorCode": -2147467261,
    "ErrorMessage": "Value cannot be null. Parameter name: resourceCollection",
    "ErrorData": null,
    "ErrorCategory": 0
}

It works correctly when I change endTime from DateTimeOffset.Now to DateTimeOffset.Now.AddHours(-2)
I also tried with DateTimeOffset.Now.AddHours(-1)
It fails with the same error.

I cannot find github repo for PartnerCenter dotnet SDK so I hope to find some help here.

ISubscriptionUsageRecordCollection' does not contain a definition for 'Resources'

Hi ,
we did not find ISubscriptionUsageRecordCollection' in PartnerSDK

code is below

using the below code url
https://docs.microsoft.com/en-us/partner-center/develop/get-a-customer-subscription-resource-usage-records#rest-response
var usageRecords = this.Context.UserPartnerOperations.Customers.ById(customerId).Subscriptions.ById(subscriptionId).UsageRecords.Resources.Get();

Error

Error CS1061 'ISubscriptionUsageRecordCollection' does not contain a definition for 'Resources' and no accessible extension method 'Resources' accepting a first argument of type 'ISubscriptionUsageRecordCollection' could be found (are you missing a using directive or an assembly reference?)

Azure Vault Exception

Getting following exception while running CSP application.

===================== Partner center API calls ============================
Microsoft.Azure.KeyVault.Models.KeyVaultErrorException: Operation returned an invalid status code 'NotFound'
at Microsoft.Azure.KeyVault.KeyVaultClient.d__65.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at Microsoft.Azure.KeyVault.KeyVaultClientExtensions.d__12.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at System.Runtime.CompilerServices.TaskAwaiter1.GetResult() at CPVApplication.Utilities.KeyVaultProvider.<GetSecretAsync>d__3.MoveNext() in C:\Users\salman\Desktop\SAM - Azure\Partner-Center-DotNet-Samples-dev-samples-update\secure-app-model\keyvault\CSPApplication\Utilities\KeyVaultProvider.cs:line 27 --- End of stack trace from previous location where exception was thrown --- at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task) at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task) at System.Runtime.CompilerServices.TaskAwaiter1.GetResult()
at CPVApplication.Program.d__4.MoveNext() in C:\Users\salman\Desktop\SAM - Azure\Partner-Center-DotNet-Samples-dev-samples-update\secure-app-model\keyvault\CSPApplication\Program.cs:line 75
--- End of stack trace from previous location where exception was thrown ---
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at System.Runtime.CompilerServices.TaskAwaiter1.GetResult() at CPVApplication.Program.<GetUserPartnerOperationsAsync>d__7.MoveNext() in C:\Users\salman\Desktop\SAM - Azure\Partner-Center-DotNet-Samples-dev-samples-update\secure-app-model\keyvault\CSPApplication\Program.cs:line 144 --- End of stack trace from previous location where exception was thrown --- at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task) at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task) at System.Runtime.CompilerServices.TaskAwaiter1.GetResult()
at CPVApplication.Program.d__3.MoveNext() in C:\Users\salman\Desktop\SAM - Azure\Partner-Center-DotNet-Samples-dev-samples-update\secure-app-model\keyvault\CSPApplication\Program.cs:line 45
Console.ReadLine();

Partner Consent App Does not Redirect with ADFS

Steps to reproduce

Configured Application with the Config Values, ran project and it prompts for login. Enter my username, redirects because domain is on ADFS, project redirects to blank page, no token exchange occurs. I am trying to just use the example to understand how everything works but since we are ADFS it appears not to be working. Are there additional actions that must be taken for domains configured to use ADFS?

No throtting example with the partner center SDK

Feature Request

Is your feature request related to a problem? Please describe.
There is no throtting example with the partner center SDK. The guidence provides an explanation on how to threat an http response https://docs.microsoft.com/en-us/partner-center/develop/api-throttling-guidance but not on how to catch the right exception and which property we must read the error code and the retry-after values

Describe the solution you would like
Example on how to catch the right exception (ex: PartnerCenterException?) and which property we must read the error code and the retry-after values

refundableQuantity Property Missing in SDK for NCE

With the new rules around subscription reduction in the New Commerce Experience (NCE) we need to view the "refundableQuantity" property to ensure we can reduce a subscription count within 72 hours of it being added. This property is available through the REST API (https://docs.microsoft.com/en-us/partner-center/develop/get-a-subscription-by-id#response-example-for-a-new-commerce-subscription) however I do not see it available in the SDK. Are there plans to get this added so we don't have to create a manual workaround?

thank you

Create Customer scenario

tried creating a customer and i get this error

Create a new customer

New customer Information

CompanyProfile:
    Domain: SampleApplication130339732.onmicrosoft.com
    Attributes:
        ObjectType: CustomerCompanyProfile
BillingProfile:
    Email: [email protected]
    Culture: en-US
    Language: en
    CompanyName: Relecloud130339732
    DefaultAddress:
        Country: US
        City: Redmond
        State: WA
        AddressLine1: 4567 Main Street
        PostalCode: 98052
        FirstName: Gena
        MiddleName: MiddleName
        LastName: Soto
        PhoneNumber: 4255550101
    Attributes:
        ObjectType: CustomerBillingProfile
RelationshipToPartner: Unknown
Attributes:
    ObjectType: Customer

Creating customer.

**Partner Exception:
Error Category: Forbidden
Service Error Payload:
Error code: 600006
Error message: The requested action is not allowed

Context: Request Id: cc3d6e10-a6d9-475d-92cb-39412f643fc3, Correlation Id: e7fa0a90-f5fe-40ff-a1cf-afc0eb903b6f, Locale: en-US
Base Description: Microsoft.Store.PartnerCenter.Exceptions.PartnerException: The requested action is not allowed
at Microsoft.Store.PartnerCenter.PartnerService.SynchronousExecute[T](Func`1 operation)
at Microsoft.Store.PartnerCenter.Samples.Customers.CreateCustomer.RunScenario() in C:\Projects\new\Partner-Center-DotNet-Samples\sdk\SdkSamples\Customers\CreateCustomer.cs:line 65
at Microsoft.Store.PartnerCenter.Samples.BasePartnerScenario.Run() in C:\Projects\new\Partner-Center-DotNet-Samples\sdk\SdkSamples\BasePartnerScenario.cs:line 78**

please help

Alternative to pop for user credentials

Hi isaiah,

I am looking at the SDK samples with new changes you made for secure model.
In LoginUserToAad() a popup appears for user credentials.

I have an old version where i am using userCredentials to acquire a token by using authContext.AcquireToken. In that case there is no window appears. The application is console app that runs, login and download the information that i need.

In the new SDK samples due to the pop up the program asks for user credentials in the popup. Is there any way to avoid it or go around it? So that the pop up wont appear and my console app can run in a windows scheduler.

Regards,
Salman

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.