bcuff / elasticsearch-net-aws

Add-on to Elasticsearch.Net & NEST for using AWS's elasticsearch service.
Apache License 2.0
72 stars 27 forks source link

User: anonymous is not authorized to perform: es:ESHttpPost (Only an issue in IIS) #42

Closed justintoth closed 5 years ago

justintoth commented 5 years ago

I'm using this nuget package for connecting to an Elasticsearch instance hosted on AWS.

var pool = new SingleNodeConnectionPool(new Uri(Url));
var httpConnection = new AwsHttpConnection(Region);
var config = new ConnectionSettings(pool, httpConnection)
                            .PrettyJson()
                            .DisableDirectStreaming()
                            .DefaultTypeName(TYPE)
                            .DefaultIndex(INDEX);
_client = new ElasticClient(config);

For setting the access key and secret, I have a credentials file stored on my Windows computer here: C:\Users{username}.aws\credential, which has a "default" entry. I've also tried in appsettings.json specifying AppSettings:AWSAccessKey & AppSettings:AWSSecretKey or specifying AWS:Profile (to a profile name that I set up using the AWS SDK Explorer in Visual Studio.) All three of these approaches are working great when I run my ASP.NET Core web application with the Project Properties > Debug > Launch option set to "Project". The "IIS Express" Launch option works as well.

If I check the credentials passed in, it shows the correct Access Key and Secret:

var credentials = FallbackCredentialsFactory.GetCredentials();
var immutableCredentials = credentials.GetCredentials();

Now, if I change my ASP.NET Core app to have the Launch option set to "IIS", all of a sudden my searches stop working.

HResult=0x80131500 Message=Invalid NEST response built from a unsuccessful low level call on POST: /rprsearchresidential/residentialsearch/_search?pretty=true&typed_keys=true

Audit trail of this API call:

  • [1] BadResponse: Node: https://{mynode}.us-east-1.es.amazonaws.com/ Took: 00:00:00.1804828

    OriginalException: Elasticsearch.Net.ElasticsearchClientException: Request failed to execute. Call: Status code 403 from: POST /rprsearchresidential/residentialsearch/_search?pretty=true&typed_keys=true

    Response:

    {"Message":"User: anonymous is not authorized to perform: es:ESHttpPost"}

If I attempt to retrieve the immutableCredentials, it throws an exception when calling credentials.GetCredentials();

Message=A socket operation was attempted to an unreachable network Source=System.Net.Http StackTrace: at System.Net.Http.ConnectHelper.d__2.MoveNext() at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw() at ... at Amazon.Util.AWSSDKUtils.DownloadStringContent(Uri uri, TimeSpan timeout, IWebProxy proxy) at Amazon.Util.EC2InstanceMetadata.GetItems(String relativeOrAbsolutePath, Int32 tries, Boolean slurp) at Amazon.Util.EC2InstanceMetadata.get_IAMSecurityCredentials() at Amazon.Runtime.DefaultInstanceProfileAWSCredentials.FetchCredentials() at Amazon.Runtime.DefaultInstanceProfileAWSCredentials.GetCredentials() at RealtorsPropertyResource.Rpr.SearchesElasticsearch.ESClient.get_Instance() in C:\RPR2\Libraries\SearchesElasticsearch\Entities\ESClient.cs:line 35

It doesn't matter which method I use for storing the AWS Access key and secret, they all error in this manner. Am I missing something required in order to connect through IIS or is this a bug in the nuget package?

bcuff commented 5 years ago

When you run under IIS you are able to consume other AWS services using the AWSSDK but not Elasticsearch using this package?

The credential loading should be exactly the same as what other AWSSDK based client's use.

When running your application using IIS it's probably running as an IIS user which won't have access to your personal ~/.aws/* credentials.

justintoth commented 5 years ago

Yeah AWS S3 is working fine. I'm running the app pool under my windows account "Justin", which is an Administrator, so it should have access to C:/Users/Justin/.aws/*. I ended up getting it to work by updating the web.config to the following:

<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <location path="." inheritInChildApplications="false">
    <system.webServer>
      <handlers>
        <add name="aspNetCore" path="*" verb="*" modules="AspNetCoreModuleV2" resourceType="Unspecified" />
      </handlers>
      <aspNetCore processPath="C:\Program Files\dotnet\dotnet.exe" arguments="exec &quot;C:\RPR2\Websites\MobileApi\bin\RealtorsPropertyResource.Rpr.MobileApi.dll&quot;" stdoutLogEnabled="false" hostingModel="InProcess">
        <environmentVariables>
          <environmentVariable name="ASPNETCORE_ENVIRONMENT" value="Development" />
          <environmentVariable name="AWS_ACCESS_KEY_ID" value="{value}" />
          <environmentVariable name="AWS_SECRET_ACCESS_KEY" value="{value}" />
        </environmentVariables>
      </aspNetCore>
    </system.webServer>
  </location>
</configuration>

I don't know why it doesn't use the .aws folder or appsettings.json in this scenario, it must be related to the magic it's doing in the web.config in order to run ASP.NET Core in IIS.