Packages
erlcloud
0.9.2-rc.1
3.8.3
3.8.2
3.8.1
3.7.6
3.7.4
3.7.3
3.7.2
3.7.1
3.7.0
3.6.8
3.6.7
3.6.5
3.6.4
3.6.3
3.6.2
3.6.1
3.6.0
3.5.16
3.5.15
3.5.14
3.5.13
3.5.12
3.5.11
3.5.10
3.5.9
3.5.8
3.5.7
3.5.6
3.5.5
3.5.4
3.5.3
3.5.2
3.5.1
3.5.0
3.4.5
3.4.3
3.4.1
3.4.0
3.3.9
3.3.8
3.3.7
3.3.6
3.3.5
3.3.4
3.3.3
3.3.2
3.3.1
3.3.0
3.2.18
3.2.17
3.2.16
3.2.15
3.2.14
3.2.13
3.2.12
3.2.11
3.2.10
3.2.7
3.2.6
3.2.5
3.2.4
3.2.3
3.2.2
3.2.1
3.2.0
3.1.17
3.1.16
3.1.14
3.1.13
3.1.12
3.1.11
3.1.9
3.1.8
3.1.7
3.1.6
3.1.5
3.1.4
3.1.3
3.1.2
3.1.1
3.1.0
3.0.5
3.0.4
3.0.3
3.0.2
3.0.1
2.2.16
2.2.15
2.2.14
2.2.13
2.2.12
2.2.11
2.2.10
2.2.9
2.2.8
2.2.7
2.2.6
2.2.5
2.2.4
2.2.2
2.2.1
2.2.0
2.1.0
2.0.5
2.0.4
2.0.3
2.0.0
0.13.10
0.13.9
0.13.8
0.13.6
0.13.5
0.13.4
0.13.3
0.13.2
0.13.0
0.12.0
0.11.0
0.9.2
0.9.2-rc.1
0.9.1
0.9.0
AWS APIs library for Erlang
Current section
Files
Jump to
Current section
Files
src/erlcloud_mon.erl
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% File: erlcloud_mon.erl
%% Date: 14-Sep-2011
%%
%% @doc AWS CloudWatch erlang binding (the CLI SDK uses "mon_" prefix)
%%
%% @author Zvi Avraham <zvi-AT-nivertech-DOT-com>
%% @copyright 2011 Zvi Avraham
%% @end
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-module(erlcloud_mon).
%%% Library initialization.
-export([configure/2, configure/3, new/2, new/3]).
-export([
list_metrics/4,
put_metric_data/2,
put_metric_data/5,
get_metric_statistics/8,
configure_host/3,
test/0,
test2/0
]).
-include_lib("erlcloud/include/erlcloud.hrl").
-include_lib("erlcloud/include/erlcloud_aws.hrl").
-include_lib("erlcloud/include/erlcloud_mon.hrl").
-include_lib("xmerl/include/xmerl.hrl").
-import(erlcloud_xml, [get_text/2]).
-define(XMLNS_MON, "http://monitoring.amazonaws.com/doc/2010-08-01/").
-define(API_VERSION, "2010-08-01").
-define(FMT(Fmt,Args), lists:flatten(io_lib:format((Fmt),(Args)))).
%%------------------------------------------------------------------------------
%% @doc CloudWatch API - ListMetrics
%% [http://docs.amazonwebservices.com/AmazonCloudWatch/latest/APIReference/index.html?API_ListMetrics.html]
%%
%% USAGE:
%%
%% erlcloud_mon:list_metrics("AWS/EC2", "NetworkIn", [{"InstanceType","m1.large"}], "").
%% [[{metric_name,"NetworkIn"},
%% {namespace,"AWS/EC2"},
%% {dimensions,[[{name,"InstanceType"},{value,"m1.large"}]]}]]
%%
%% @end
%%------------------------------------------------------------------------------
-spec list_metrics(
Namespace ::string(),
MetricName ::string(),
DimensionFilter ::[{string(),string()}],
NextToken ::string()
) -> term().
list_metrics(
Namespace,
MetricName,
DimensionFilter,
NextToken
) ->
Config = default_config(),
Params =
[{"Namespace", Namespace} || Namespace/=""]
++
[{"MetricName", MetricName} || MetricName/=""]
++
[{"NextToken", NextToken} || NextToken/=""]
++
lists:flatten(
[begin
{Name, Value} = lists:nth(N, DimensionFilter),
[{?FMT("Dimensions.member.~b.Name", [N]), Name},
{?FMT("Dimensions.member.~b.Value", [N]), Value}]
end
|| N<-lists:seq(1, length(DimensionFilter))]
),
Doc = mon_query(Config, "ListMetrics", Params),
Members = xmerl_xpath:string("/ListMetricsResponse/ListMetricsResult/Metrics/member", Doc),
[extract_member(Member) || Member <- Members].
extract_member(Node) ->
[
{metric_name, get_text("MetricName", Node)},
{namespace, get_text("Namespace", Node)},
{dimensions,
[extract_dimension(Item) || Item <- xmerl_xpath:string("Dimensions/member", Node)]
}
].
extract_dimension(Node) ->
[
{name, get_text("Name", Node)},
{value, get_text("Value", Node)}
].
%%------------------------------------------------------------------------------
%% @doc CloudWatch API - PutMetricData
%% [http://docs.amazonwebservices.com/AmazonCloudWatch/latest/APIReference/index.html?API_PutMetricData.html]
%% `
%% &MetricData.member.1.MetricName=buffers
%% &MetricData.member.1.Unit=Bytes
%% &MetricData.member.1.Value=231434333
%% &MetricData.member.1.Dimensions.member.1.Name=InstanceID
%% &MetricData.member.1.Dimensions.member.1.Value=i-aaba32d4
%% &MetricData.member.1.Dimensions.member.2.Name=InstanceType
%% &MetricData.member.1.Dimensions.member.2.Value=m1.small
%% &MetricData.member.2.MetricName=latency
%% &MetricData.member.2.Unit=Milliseconds
%% &MetricData.member.2.Value=23
%% &MetricData.member.2.Dimensions.member.1.Name=InstanceID
%% &MetricData.member.2.Dimensions.member.1.Value=i-aaba32d4
%% &MetricData.member.2.Dimensions.member.2.Name=InstanceType
%% &MetricData.member.2.Dimensions.member.2.Value=m1.small
%% '
%% @end
%%------------------------------------------------------------------------------
-spec put_metric_data(
Namespace ::string(),
MetricData ::[metric_datum()]
) -> term().
put_metric_data(Namespace, MetricData) ->
Config = default_config(),
Params =
[
{"Namespace", Namespace} |
lists:flatten(
[ params_metric_data(N,MD) || {N,MD} <- lists:zip(lists:seq(1,length(MetricData)), MetricData) ]
)
],
mon_query(Config, "PutMetricData", Params).
%%------------------------------------------------------------------------------
-spec params_metric_data(NM::pos_integer(), MD::metric_datum()) -> [{string(),string()}].
params_metric_data(NM,MD) ->
%% TODO - check case when both Value and statistics specified or both undefined
Prefix = ?FMT("MetricData.member.~b", [NM]),
lists:flatten(
[
[ {Prefix++".MetricName", MD#metric_datum.metric_name} ],
[ {Prefix++".Unit", MD#metric_datum.unit} || MD#metric_datum.unit=/=undefined ],
[ {Prefix++".Timestamp", format_timestamp(MD#metric_datum.timestamp)}|| MD#metric_datum.timestamp=/=undefined ],
[ {Prefix++".Value", float_to_list(MD#metric_datum.value)} || MD#metric_datum.value=/=undefined ],
[ params_stat(Prefix, MD#metric_datum.statistic_values) || MD#metric_datum.statistic_values=/=undefined ],
[ params_dimension(Prefix, ND, Dimension)
|| {ND,Dimension} <- lists:zip(lists:seq(1, length(MD#metric_datum.dimensions)), MD#metric_datum.dimensions)
]
]
).
%%------------------------------------------------------------------------------
%% @doc format datetime as Amazon timestamp
%% @end
%%------------------------------------------------------------------------------
format_timestamp({{Yr, Mo, Da}, {H, M, S}} = Timestamp)
when is_integer(Yr), is_integer(Mo), is_integer(Da),
is_integer(H), is_integer(M), is_integer(S)
->
erlcloud_aws:format_timestamp(Timestamp);
format_timestamp(Timestamp) when is_list(Timestamp) ->
Timestamp.
%%------------------------------------------------------------------------------
-spec params_dimension(Prefix::string(), ND::pos_integer(), Dimension::dimension()) -> [{string(),string()}].
params_dimension(Prefix, ND, Dimension) ->
DimPrefix = ?FMT("~s.Dimensions.member.~b", [Prefix, ND]),
[
{DimPrefix++".Name", Dimension#dimension.name},
{DimPrefix++".Value", Dimension#dimension.value}
].
%%------------------------------------------------------------------------------
%% @doc format statistic value records to URI params
%% @end
%%------------------------------------------------------------------------------
-spec params_stat(Prefix::string(), StatisticValues::statistic_set()) -> [{string(),string()}].
params_stat(Prefix, StatisticValues) ->
[
{Prefix++".StatisticValues.Maximum", float_to_list(StatisticValues#statistic_set.maximum)},
{Prefix++".StatisticValues.Minimum", float_to_list(StatisticValues#statistic_set.maximum)},
{Prefix++".StatisticValues.Sum", float_to_list(StatisticValues#statistic_set.sum)},
{Prefix++".StatisticValues.SampleCount",integer_to_list(StatisticValues#statistic_set.sample_count)}
].
%%------------------------------------------------------------------------------
%% @doc CloudWatch API - PutMetricData
%% [http://docs.amazonwebservices.com/AmazonCloudWatch/latest/APIReference/index.html?API_PutMetricData.html]
%% @end
%%------------------------------------------------------------------------------
-spec put_metric_data(
Namespace ::string(),
MetricName ::string(),
Value ::string(),
Unit ::unit(),
Timestamp ::datetime()|string()
) -> term().
put_metric_data(Namespace, MetricName, Value, Unit, Timestamp) ->
Config = default_config(),
Params =
lists:flatten(
[
{"Namespace", Namespace},
{"MetricData.member.1.MetricName", MetricName},
{"MetricData.member.1.Value", Value},
[ {"MetricData.member.1.Unit", Unit} || Unit=/=undefined, Unit=/="" ],
[ {"MetricData.member.1.Timestamp", format_timestamp(Timestamp)} || Timestamp=/=undefined, Timestamp=/="" ]
]
),
mon_simple_query(Config, "PutMetricData", Params).
%%------------------------------------------------------------------------------
%% @doc CloudWatch API - GetMetricStatistics
%% [http://docs.amazonwebservices.com/AmazonCloudWatch/latest/APIReference/index.html?API_GetMetricStatistics.html]
%% @end
%%------------------------------------------------------------------------------
-spec get_metric_statistics(
Namespace ::string(),
MetricName ::string(),
StartTime ::string(),
EndTime ::string(),
Period ::pos_integer(),
Unit ::string(),
Statistics ::[string()],
Dimensions ::[string()]
) -> term().
get_metric_statistics(
_Namespace,
_MetricName,
_StartTime,
_EndTime,
_Period,
_Unit,
_Statistics,
_Dimensions
) ->
todo.
%%------------------------------------------------------------------------------
mon_simple_query(Config, Action, Params) ->
mon_query(Config, Action, Params),
ok.
mon_query(Config, Action, Params) ->
mon_query(Config, Action, Params, ?API_VERSION).
mon_query(Config, Action, Params, ApiVersion) ->
QParams = [{"Action", Action}, {"Version", ApiVersion}|Params],
erlcloud_aws:aws_request_xml(get,
Config#aws_config.mon_protocol,
Config#aws_config.mon_host,
Config#aws_config.mon_port,
"/",
QParams,
Config).
configure_host(Host, Port, Protocol) ->
Config = default_config(),
NewConfig = Config#aws_config{mon_host=Host,
mon_port=Port,
mon_protocol=Protocol},
put(aws_config, NewConfig).
-spec(new/2 :: (string(), string()) -> aws_config()).
new(AccessKeyID, SecretAccessKey) ->
#aws_config{access_key_id=AccessKeyID,
secret_access_key=SecretAccessKey}.
-spec(new/3 :: (string(), string(), string()) -> aws_config()).
new(AccessKeyID, SecretAccessKey, Host) ->
#aws_config{access_key_id=AccessKeyID,
secret_access_key=SecretAccessKey,
mon_host=Host}.
-spec(configure/2 :: (string(), string()) -> ok).
configure(AccessKeyID, SecretAccessKey) ->
put(aws_config, new(AccessKeyID, SecretAccessKey)),
ok.
-spec(configure/3 :: (string(), string(), string()) -> ok).
configure(AccessKeyID, SecretAccessKey, Host) ->
put(aws_config, new(AccessKeyID, SecretAccessKey, Host)),
ok.
default_config() -> erlcloud_aws:default_config().
%%------------------------------------------------------------------------------
%% tests
%% TODO : convert into e-unit tests
%%------------------------------------------------------------------------------
test() ->
M1 = #metric_datum{
metric_name = "zvi",
dimensions = [],
statistic_values = undefined,
timestamp = undefined,
unit = "Count",
value = 10.0
},
M2 = #metric_datum{
metric_name = "zvi",
dimensions = [],
statistic_values = #statistic_set{minimum=18.0, maximum=21.4, sum=67.7, sample_count=15},
timestamp = undefined,
unit = "Count",
value = undefined
},
put_metric_data("my", [M1, M2]).
%put_metric_data("my", [M2]).
test2() ->
put_metric_data("my", "zvi", "13", "Count", "").