Skip to content

Instantly share code, notes, and snippets.

@joewilliams
Created July 20, 2009 16:45
Show Gist options
  • Save joewilliams/150435 to your computer and use it in GitHub Desktop.
Save joewilliams/150435 to your computer and use it in GitHub Desktop.
erlaws partial ec2 support
-define(API_VERSION, "2009-04-04").
-define(API_URL, "http://ec2.amazonaws.com/").
%% The following code was taken from erlaws erlaws_sdb.erl
%% and in some cases modified to work slightly different
%%
%% http://github.com/x6j8x/erlaws/tree/master
%%
%% Copyright (C) 2008 Sascha Matzke
%%
%% Redistribution and use in source and binary forms, with or without
%% modification, are permitted provided that the following conditions are met:
%%
%% 1. Redistributions of source code must retain the above copyright notice,
%% this list of conditions and the following disclaimer.
%%
%% 2. Redistributions in binary form must reproduce the above copyright notice,
%% this list of conditions and the following disclaimer in the documentation
%% and/or other materials provided with the distribution.
%%
%% THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
%% INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
%% FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
%% DEVELOPERS AND CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
%% SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
%% PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
%% OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
%% WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
%% OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
%% ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
generic_request(Action, Params, Key, Secret) ->
Timestamp = lists:flatten(get_timestamp()),
ActionQueryParams = getQueryParams(Action, Params),
SignParams = [{"AWSAccessKeyId", Key},
{"Action", Action},
{"Version", ?API_VERSION},
{"SignatureVersion", "1"},
{"Timestamp", Timestamp}] ++ ActionQueryParams,
StringToSign = mkEnumeration([Param++Value || {Param, Value} <- lists:sort(fun (A, B) ->
{KeyA, _} = A,
{KeyB, _} = B,
string:to_lower(KeyA) =< string:to_lower(KeyB) end,
SignParams)], ""),
Signature = sign(Secret, StringToSign),
FinalQueryParams = SignParams ++ [{"Signature", Signature}],
Result = mkReq(FinalQueryParams),
case Result of
{ok, _Status, Body} ->
{ok, Body};
{error, {_Proto, Code, Reason}, Body} ->
throw({error, {integer_to_list(Code), Reason}, Body})
end.
getQueryParams("DescribeInstances", _) ->
[];
getQueryParams("RunInstances", [KeyName, Count, ImageId, InstanceType, AvailabilityZone]) ->
[
{"KeyName", KeyName},
{"MinCount", Count},
{"MaxCount", Count},
{"ImageId", ImageId},
{"InstanceType", InstanceType},
{"Placement.AvailabilityZone", AvailabilityZone}
];
getQueryParams("TerminateInstances", [InstanceId]) ->
[
{"InstanceId", InstanceId}
].
sign(Key,Data) ->
%io:format("StringToSign:~n ~p~n", [Data]),
binary_to_list( base64:encode( crypto:sha_mac(Key,Data) ) ).
mkReq(QueryParams) ->
%io:format("QueryParams:~n ~p~n", [QueryParams]),
Url = ?API_URL ++ queryParams( QueryParams ),
%io:format("RequestUrl:~n ~p~n", [Url]),
Request = {Url, []},
HttpOptions = [{autoredirect, true}],
Options = [ {sync,true}, {headers_as_is,true}, {body_format, binary} ],
{ok, {Status, _ReplyHeaders, Body}} =
http:request(get, Request, HttpOptions, Options),
%io:format("Response:~n ~p~n", [binary_to_list(Body)]),
case Status of
{_, 200, _} -> {ok, Status, binary_to_list(Body)};
{_, _, _} -> {error, Status, binary_to_list(Body)}
end.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment