Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

CloudSearch is forced as a "GET" #235

Closed
martinjt opened this issue Aug 20, 2015 · 3 comments
Closed

CloudSearch is forced as a "GET" #235

martinjt opened this issue Aug 20, 2015 · 3 comments
Labels
feature-request A feature should be added or improved.

Comments

@martinjt
Copy link

This means that large queries fail due to the "RequestEntityTooLarge" error.

Is there a way to allow the caller to change this? maybe using the ClientConfig?

@PavelSafronov PavelSafronov added the feature-request A feature should be added or improved. label Aug 25, 2015
@PavelSafronov
Copy link

Thanks for opening this issue. This is a known limitation with the GET method. At the moment, there is no way to configure the client to use POST instead, but we are adding this feature to our internal backlog and will keep this issue updated.

@martinjt
Copy link
Author

Ok, well I worked around it by creating my own derived class and marshaller.

    public class CloudSearchClient : AmazonCloudSearchDomainClient
    {
        public CloudSearchClient(AWSCredentials creds, AmazonCloudSearchDomainConfig config) :
            base(creds, config)
        {
        }

        public new SearchResponse Search(SearchRequest request)
        {
            var marshaller = new PostSearchRequestMarshaller();
            var unmarshaller = SearchResponseUnmarshaller.Instance;

            return Invoke<SearchRequest, SearchResponse>(request, marshaller, unmarshaller);
        }

        public new Task<SearchResponse> SearchAsync(SearchRequest request, CancellationToken cancellationToken = new CancellationToken())
        {
            var marshaller = new PostSearchRequestMarshaller();
            var unmarshaller = SearchResponseUnmarshaller.Instance;

            return InvokeAsync<SearchRequest, SearchResponse>(request, marshaller, unmarshaller, cancellationToken);
        }
    }

and the Marshaller

    public class PostSearchRequestMarshaller : IMarshaller<IRequest, SearchRequest>,
        IMarshaller<IRequest, AmazonWebServiceRequest>
    {
        /// <summary>
        /// Marshaller the request object to the HTTP request.
        /// </summary>  
        /// <param name="input"></param>
        /// <returns></returns>
        public IRequest Marshall(AmazonWebServiceRequest input)
        {
            return Marshall((SearchRequest) input);
        }

        public IRequest Marshall(SearchRequest publicRequest)
        {
            IRequest request = new DefaultRequest(publicRequest, "Amazon.CloudSearchDomain");
            request.HttpMethod = "POST";

            string uriResourcePath = "/2013-01-01/search";
            request.Parameters.Add("format", "sdk");
            request.Parameters.Add("pretty", "true");

            if (publicRequest.FilterQuery != null)
                request.Parameters.Add("fq", StringUtils.FromString(publicRequest.FilterQuery));

            if (publicRequest.Query != null)
                request.Parameters.Add("q", StringUtils.FromString(publicRequest.Query));

            if (publicRequest.QueryOptions != null)
                request.Parameters.Add("q.options", StringUtils.FromString(publicRequest.QueryOptions));

            if (publicRequest.QueryParser != null)
                request.Parameters.Add("q.parser", StringUtils.FromString(publicRequest.QueryParser));

            if (publicRequest.Return != null)
                request.Parameters.Add("return", StringUtils.FromString(publicRequest.Return));

            if (publicRequest.Facet != null)
                request.Parameters.Add("facet", StringUtils.FromString(publicRequest.Facet));

            if (publicRequest.Sort != null)
                request.Parameters.Add("sort", StringUtils.FromString(publicRequest.Sort));


            request.Parameters.Add("size", StringUtils.FromLong(publicRequest.Size));

            request.ResourcePath = uriResourcePath;
            request.UseQueryString = false;
            request.SetContentFromParameters = true;

            return request;
        }

It does have some issues in that I've not added all the available properties to the request, but it does the job, and means that we can continue using the SDK without resorting to RestSharp.

I've copied most the code from your source, and traced the SDK code. I haven't had any issues with it yet.

@jimfl
Copy link
Contributor

jimfl commented Oct 23, 2015

@jimfl jimfl closed this as completed Oct 23, 2015
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
feature-request A feature should be added or improved.
Projects
None yet
Development

No branches or pull requests

3 participants