Giter VIP home page Giter VIP logo

awscr-signer's Introduction

awscr-signer

Build Status

Crystal interface for AWS Signing.

Supports signing or presigning Crystal HTTP::Request objects.

Installation

Add this to your application's shard.yml:

dependencies:
  awscr-signer:
    github: taylorfinnell/awscr-signer

Usage

Create a Signer::Signers::V4 object.

signer = Awscr::Signer::Signers::V4.new("service", "region", "key", "secret")

or

Create a Signer::Signers::V2 object.

signer = Awscr::Signer::Signers::V2.new("service", "region", "key", "secret")

Signing an HTTP::Request.

signer.sign(request)

Signing an String.

signer.sign("my string")

Presign a HTTP::Request.

signer.presign(request)

Examples

S3

For S3 specific support see awscr-s3.

Known Limitations

The following items are known issues.

  • The request URI can not contain repeating slashes.
  • The request headers can not have new line separted values.
  • The request path can not contain spaces.

awscr-signer's People

Contributors

carlhoerberg avatar caspiano avatar chrisbirster avatar jackturnbull avatar jrester avatar marzhaev avatar taylorfinnell avatar xaviablaza avatar y2k2mt avatar

Stargazers

 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

awscr-signer's Issues

SES send email

I'm curious if this is something you've tried or how it can be achieved, I keep getting error code 400 - BAD REQUEST

I'm able to use this similar code to retrieve private files from S3

Here is what i'm currently doing:

SES_REGION = "us-west-2"
SES_HOST   = "email.#{SES_REGION}.amazonaws.com"
KEY        = ENV["AWS_ACCESS_KEY"]
SECRET     = ENV["AWS_SECRET_KEY"]

private def creds
  Awscr::Signer::Credentials.new(KEY, SECRET)
end

private def ses_scope
  Awscr::Signer::Scope.new(SES_REGION, "ses")
end

url = String.build do |io|
  HTTP::Params.from_hash({
    "Action"                           => "SendEmail",
    "Source"                           => "[email protected]",
    "Destination.ToAddresses.member.1" => "[email protected]",
    "Message.Subject.Data"             => "test",
    "Message.Body.Text.Data"           => "test",
  }).to_s(io)
end

client = HTTP::Client.new(SES_HOST, 443, true)
client.before_request do |request|
  request.headers["Host"] = SES_HOST
  signer = Awscr::Signer::V4.new(request, ses_scope, creds)
  signer.sign
end

resp = client.get(url)

Support for Instance IAM credential fallback.

Fall back to using the meta-data interface to fill in credential information if none is provided.
This will allow users to invoke AWS calls via say the sqs shard without having credentials in cases
where the instance is authorized via IAM.

version mismatch between tag and shard

current v0.8.0 tag points to 0.7.0 of shard.yml.

$ git show v0.8.0:shard.yml | grep version
version: 0.7.0

This forces shards build to fetch repository always.

Fetching https://github.com/taylorfinnell/awscr-signer.git
Installing awscr-signer (0.7.0 at 0.8.0)

Could you re-tag to f5fd505 or create a new tag v0.8.1 to current master?

InvalidSignatureException when keep-alive connection is retried

When a long lived HTTP connection times out and the http client has to reconnect the before_request will be executed again, but then there are already headers which I think this code will use: https://github.com/taylorfinnell/awscr-signer/blob/master/src/awscr-signer/signers/v4.cr#L83-L85

but that results in a InvalidSignatureException. It can be solved by deleting the headers first:

      @http.before_request do |request|
        request.headers.delete "Authorization"
        request.headers.delete "X-Amz-Content-Sha256"
        request.headers.delete "X-Amz-Date"
        signer.sign(request)
      end

DigitalOcean Spaces + `Connection: keep-alive` results in SignatureDoesNotMatch

My AWS client (hand-rolled because I need a few different services) uses a connection pool to avoid opening a new connection on every request, so it uses the Connection: keep-alive header.

When signing an S3-compatible request to DigitalOcean Spaces with that header in place, I get the following response:

<?xml version=\"1.0\" encoding=\"UTF-8\"?>
<Error>
  <Code>SignatureDoesNotMatch</Code>
  <RequestId>tx00000000000001dd041f0-005f164aec-364b4af-nyc3a</RequestId>
  <HostId>364b4af-nyc3a-nyc</HostId>
</Error>

Removing Connection: keep-alive or using AWS works just fine. It seems to be the combination of DO + the header. To be clear, I think this is actually an issue with DigitalOcean since it works fine with S3, but the fact that the official S3 libraries (which also hold connections open in a connection pool) work fine on DO Spaces seems to indicate that this shard may be doing something different with that particular header.

Issue with Crystal 0.30.0

Showing last frame. Use --error-trace for full trace.

In /usr/local/Cellar/crystal/0.30.0_1/src/comparable.cr:83:16

 83 | abstract def <=>(other : T)
                   ^--
Error: abstract `def Comparable(T)#<=>(other : T)` must be implemented by Awscr::Signer::Header```

examples/request_signing_v4.cr works on Mac OS X but not on Linux

Hi,

First of all thank you for the great work on the signer.

It works flawlessly on Mac OS X but I cannot get it to work on Linux. I have tried it in a CentOS 8 container and a the official Crystal Lang/alpine container with no luck.

Details:

Mac OS X:

crystal version -v
Crystal 1.0.0 (2021-03-22)

LLVM: 9.0.1
Default target: x86_64-apple-macosx
shards list
Shards installed:
  * awscr-signer (0.8.2)

Linux:

I'm using the Alpine Linux Docker container:

crystallang/crystal:latest-alpine
crystal --version
Crystal 1.0.0 [dd40a2442] (2021-03-22)

LLVM: 10.0.0
Default target: x86_64-unknown-linux-musl
shards list
Shards installed:
  * awscr-signer (0.8.2)

The error on Linux is:

<Error><Code>SignatureDoesNotMatch</Code><Message>The request signature we calculated does not match the signature you provided. Check your key and signing method.</Message><AWSAccessKeyId><----REDACTED----></AWSAccessKeyId><StringToSign>AWS4-HMAC-SHA256
20210514T222850Z
20210514/us-west-2/s3/aws4_request

I use the exact same credentials in both cases. Any thoughts on what may be going wrong?

Thanks!

S3 pre-signed download url

Trying to generate an expiring s3 url, if I add ?Expires=#{epoch_time}" to the request url, it seems Expires` is removed from the url and is not added into headers.

Perhaps I'm doing something wrong.

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.