PageRenderTime 23ms CodeModel.GetById 25ms RepoModel.GetById 0ms app.codeStats 1ms

/src/ResourceManager/Insights/Commands.Insights.Test/Utilities.cs

https://gitlab.com/jslee1/azure-powershell
C# | 435 lines | 355 code | 48 blank | 32 comment | 3 complexity | ebbe65318b6181bcc864ba7e958ae2c2 MD5 | raw file
  1. // ----------------------------------------------------------------------------------
  2. //
  3. // Copyright Microsoft Corporation
  4. // Licensed under the Apache License, Version 2.0 (the "License");
  5. // you may not use this file except in compliance with the License.
  6. // You may obtain a copy of the License at
  7. // http://www.apache.org/licenses/LICENSE-2.0
  8. // Unless required by applicable law or agreed to in writing, software
  9. // distributed under the License is distributed on an "AS IS" BASIS,
  10. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  11. // See the License for the specific language governing permissions and
  12. // limitations under the License.
  13. // ----------------------------------------------------------------------------------
  14. using Microsoft.Azure.Commands.Insights.Alerts;
  15. using Microsoft.Azure.Commands.Insights.OutputClasses;
  16. using Microsoft.Azure.Insights;
  17. using Microsoft.Azure.Insights.Models;
  18. using Microsoft.Azure.Management.Insights.Models;
  19. using Moq;
  20. using System;
  21. using System.Collections.Generic;
  22. using System.ComponentModel;
  23. using System.Net;
  24. using System.Threading;
  25. using System.Threading.Tasks;
  26. using Xunit;
  27. namespace Microsoft.Azure.Commands.Insights.Test
  28. {
  29. public static class Utilities
  30. {
  31. public static readonly string Name = "checkrule3-4b135401-a30c-4224-ae21-fa53a5bd253d";
  32. public static readonly string Caller = "caller";
  33. public static readonly string Correlation = "correlation";
  34. public static readonly string ResourceGroup = "Default-Web-EastUS";
  35. public static readonly string ResourceProvider = "Microsoft Resources";
  36. public static readonly string ResourceUri = "/subscriptions/a93fb07c-6c93-40be-bf3b-4f0deba10f4b/resourceGroups/Default-Web-EastUS/providers/microsoft.web/sites/garyyang1";
  37. public static readonly string Status = "Succeeded";
  38. public static readonly string ContinuationToken = "more records";
  39. #region Events
  40. public static EventData CreateFakeEvent()
  41. {
  42. return new EventData()
  43. {
  44. Id = "ac7d2ab5-698a-4c33-9c19-0a93d3d7f527",
  45. EventName = new LocalizableString()
  46. {
  47. LocalizedValue = "Start request",
  48. Value = "Start request",
  49. },
  50. Category = new LocalizableString()
  51. {
  52. LocalizedValue = "Microsoft Resources",
  53. Value = "Microsoft Resources",
  54. },
  55. Authorization = new SenderAuthorization()
  56. {
  57. Action = "PUT",
  58. Condition = "",
  59. Role = "Sender",
  60. Scope = "None"
  61. },
  62. Caller = Caller,
  63. Claims = new Dictionary<string, string>
  64. {
  65. {"aud", "https://management.core.windows.net/"},
  66. {"iss", "https://sts.windows.net/123456/"},
  67. {"iat", "h123445"}
  68. },
  69. CorrelationId = Correlation,
  70. Description = "fake event",
  71. EventChannels = EventChannels.Operation,
  72. Level = EventLevel.Informational,
  73. EventTimestamp = DateTime.Now,
  74. OperationId = "c0f2e85f-efb0-47d0-bf90-f983ec8be91d",
  75. OperationName = new LocalizableString()
  76. {
  77. LocalizedValue = "Microsoft.Resources/subscriptions/resourcegroups/deployments/write",
  78. Value = "Microsoft.Resources/subscriptions/resourcegroups/deployments/write",
  79. },
  80. Status = new LocalizableString()
  81. {
  82. LocalizedValue = Status,
  83. Value = Status,
  84. },
  85. SubStatus = new LocalizableString()
  86. {
  87. LocalizedValue = "Created",
  88. Value = "Created",
  89. },
  90. ResourceGroupName = ResourceGroup,
  91. ResourceProviderName = new LocalizableString()
  92. {
  93. LocalizedValue = ResourceProvider,
  94. Value = ResourceProvider,
  95. },
  96. ResourceId = ResourceUri,
  97. HttpRequest = new HttpRequestInfo
  98. {
  99. Uri = "http://path/subscriptions/ffce8037-a374-48bf-901d-dac4e3ea8c09/resourcegroups/foo/deployments/testdeploy",
  100. Method = "PUT",
  101. ClientRequestId = "1234",
  102. ClientIpAddress = "123.123.123.123"
  103. },
  104. Properties = new Dictionary<string, string>(),
  105. };
  106. }
  107. public static EventDataListResponse InitializeResponse()
  108. {
  109. // This is effectively testing the conversion EventData -> PSEventData internally in the execution of the cmdlet
  110. EventData eventData = Utilities.CreateFakeEvent();
  111. return new EventDataListResponse()
  112. {
  113. EventDataCollection = new EventDataCollection()
  114. {
  115. Value = new List<EventData>()
  116. {
  117. eventData,
  118. },
  119. NextLink = null,
  120. },
  121. RequestId = Guid.NewGuid().ToString(),
  122. StatusCode = HttpStatusCode.OK
  123. };
  124. }
  125. public static MetricListResponse InitializeMetricResponse()
  126. {
  127. // This is effectively testing the conversion EventData -> PSEventData internally in the execution of the cmdlet
  128. EventData eventData = Utilities.CreateFakeEvent();
  129. return new MetricListResponse
  130. {
  131. MetricCollection = new MetricCollection
  132. {
  133. Value = new List<Metric>()
  134. },
  135. RequestId = Guid.NewGuid().ToString(),
  136. StatusCode = HttpStatusCode.OK
  137. };
  138. }
  139. public static MetricDefinitionListResponse InitializeMetricDefinitionResponse()
  140. {
  141. // This is effectively testing the conversion EventData -> PSEventData internally in the execution of the cmdlet
  142. EventData eventData = Utilities.CreateFakeEvent();
  143. return new MetricDefinitionListResponse
  144. {
  145. MetricDefinitionCollection = new MetricDefinitionCollection
  146. {
  147. Value = new MetricDefinition[] { }
  148. },
  149. RequestId = Guid.NewGuid().ToString(),
  150. StatusCode = HttpStatusCode.OK
  151. };
  152. }
  153. public static UsageMetricListResponse InitializeUsageMetricResponse()
  154. {
  155. return new UsageMetricListResponse
  156. {
  157. UsageMetricCollection = new UsageMetricCollection
  158. {
  159. Value = new List<UsageMetric>()
  160. },
  161. RequestId = Guid.NewGuid().ToString(),
  162. StatusCode = HttpStatusCode.OK
  163. };
  164. }
  165. public static void VerifyDetailedOutput(EventCmdletBase cmdlet, ref string selected)
  166. {
  167. // Calling with detailed output
  168. cmdlet.DetailedOutput = true;
  169. cmdlet.ExecuteCmdlet();
  170. Assert.Null(selected); // Incorrect nameOrTargetUri clause with detailed output on
  171. }
  172. public static void VerifyContinuationToken(EventDataListResponse response, Mock<IEventOperations> insinsightsEventOperationsMockightsClientMock, EventCmdletBase cmdlet)
  173. {
  174. // Make sure calls to Next work also
  175. response.EventDataCollection.NextLink = Utilities.ContinuationToken;
  176. var responseNext = new EventDataListResponse()
  177. {
  178. EventDataCollection = new EventDataCollection()
  179. {
  180. Value = new List<EventData>()
  181. {
  182. Utilities.CreateFakeEvent(),
  183. },
  184. NextLink = null,
  185. },
  186. RequestId = Guid.NewGuid().ToString(),
  187. StatusCode = HttpStatusCode.OK
  188. };
  189. string nextToken = null;
  190. insinsightsEventOperationsMockightsClientMock.Setup(f => f.ListEventsNextAsync(It.IsAny<string>(), It.IsAny<CancellationToken>()))
  191. .Returns(Task.FromResult<EventDataListResponse>(responseNext))
  192. .Callback((string n, CancellationToken t) => nextToken = n);
  193. // Calling without optional parameters
  194. cmdlet.ExecuteCmdlet();
  195. Assert.True(string.Equals(Utilities.ContinuationToken, nextToken, StringComparison.OrdinalIgnoreCase), "Incorrect continuation token");
  196. }
  197. public static void VerifyFilterIsUsable(string filter)
  198. {
  199. Assert.NotNull(filter);
  200. Assert.False(string.IsNullOrWhiteSpace(filter));
  201. }
  202. public static void VerifyConditionInFilter(string filter, string field, string value)
  203. {
  204. if (!string.IsNullOrWhiteSpace(field))
  205. {
  206. var condition = string.Format("and {0} eq '{1}'", field, value);
  207. Assert.True(filter.Contains(condition), string.Format("Filter: {0} does not contain required condition: {1}", filter, condition));
  208. }
  209. }
  210. public static void VerifyStartDateInFilter(string filter, DateTime? startDate)
  211. {
  212. var condition = startDate.HasValue ? string.Format("eventTimestamp ge '{0:o}'", startDate.Value.ToUniversalTime()) : string.Format("eventTimestamp ge '");
  213. Assert.True(filter.Contains(condition), "Filter does not contain start date condition");
  214. }
  215. public static void VerifyEndDateInFilter(string filter, DateTime endDate)
  216. {
  217. var condition = string.Format(" and eventTimestamp le '{0:o}'", endDate.ToUniversalTime());
  218. Assert.True(filter.Contains(condition), "Filter does not contain end date condition");
  219. }
  220. public static void VerifyCallerInCall(string filter, DateTime? startDate, string filedName, string fieldValue)
  221. {
  222. VerifyFilterIsUsable(filter: filter);
  223. VerifyStartDateInFilter(filter: filter, startDate: startDate);
  224. VerifyConditionInFilter(filter: filter, field: filedName, value: fieldValue);
  225. VerifyConditionInFilter(filter: filter, field: "caller", value: Utilities.Caller);
  226. }
  227. public static void VerifyStatusAndCallerInCall(string filter, DateTime? startDate, string filedName, string fieldValue)
  228. {
  229. VerifyFilterIsUsable(filter: filter);
  230. VerifyStartDateInFilter(filter: filter, startDate: startDate);
  231. VerifyConditionInFilter(filter: filter, field: filedName, value: fieldValue);
  232. VerifyConditionInFilter(filter: filter, field: "caller", value: Utilities.Caller);
  233. VerifyConditionInFilter(filter: filter, field: "status", value: Utilities.Status);
  234. }
  235. public static void ExecuteVerifications(EventCmdletBase cmdlet, Mock<IEventOperations> insinsightsEventOperationsMockightsClientMock, string requiredFieldName, string requiredFieldValue, ref string filter, ref string selected, DateTime startDate, EventDataListResponse response)
  236. {
  237. // Calling without optional parameters
  238. cmdlet.ExecuteCmdlet();
  239. VerifyFilterIsUsable(filter: filter);
  240. VerifyStartDateInFilter(filter: filter, startDate: null);
  241. VerifyConditionInFilter(filter: filter, field: requiredFieldName, value: requiredFieldValue);
  242. Assert.True(string.Equals(PSEventDataNoDetails.SelectedFieldsForQuery, selected, StringComparison.OrdinalIgnoreCase), "Incorrect nameOrTargetUri clause without optional parameters");
  243. // Calling with only start date
  244. cmdlet.StartTime = startDate;
  245. cmdlet.ExecuteCmdlet();
  246. VerifyFilterIsUsable(filter: filter);
  247. VerifyStartDateInFilter(filter: filter, startDate: startDate);
  248. VerifyConditionInFilter(filter: filter, field: requiredFieldName, value: requiredFieldValue);
  249. // Calling with only start and end date
  250. cmdlet.EndTime = startDate.AddSeconds(2);
  251. cmdlet.ExecuteCmdlet();
  252. VerifyFilterIsUsable(filter: filter);
  253. VerifyStartDateInFilter(filter: filter, startDate: startDate);
  254. VerifyEndDateInFilter(filter: filter, endDate: startDate.AddSeconds(2));
  255. VerifyConditionInFilter(filter: filter, field: requiredFieldName, value: requiredFieldValue);
  256. // Calling with only caller
  257. cmdlet.EndTime = null;
  258. cmdlet.Caller = Utilities.Caller;
  259. cmdlet.ExecuteCmdlet();
  260. VerifyCallerInCall(filter: filter, startDate: startDate, filedName: requiredFieldName, fieldValue: requiredFieldValue);
  261. // Calling with caller and status
  262. cmdlet.Status = Utilities.Status;
  263. cmdlet.ExecuteCmdlet();
  264. VerifyStatusAndCallerInCall(filter: filter, startDate: startDate, filedName: requiredFieldName, fieldValue: requiredFieldValue);
  265. VerifyDetailedOutput(cmdlet: cmdlet, selected: ref selected);
  266. VerifyContinuationToken(response: response, insinsightsEventOperationsMockightsClientMock: insinsightsEventOperationsMockightsClientMock, cmdlet: cmdlet);
  267. // Execute negative tests
  268. cmdlet.StartTime = DateTime.Now.AddSeconds(1);
  269. Assert.Throws<ArgumentException>(() => cmdlet.ExecuteCmdlet());
  270. cmdlet.StartTime = DateTime.Now.Subtract(TimeSpan.FromSeconds(20));
  271. cmdlet.EndTime = DateTime.Now.Subtract(TimeSpan.FromSeconds(21));
  272. Assert.Throws<ArgumentException>(() => cmdlet.ExecuteCmdlet());
  273. cmdlet.StartTime = DateTime.Now.Subtract(TimeSpan.FromDays(30));
  274. cmdlet.EndTime = DateTime.Now.Subtract(TimeSpan.FromDays(14));
  275. Assert.Throws<ArgumentException>(() => cmdlet.ExecuteCmdlet());
  276. }
  277. #endregion
  278. #region Alerts
  279. public static RuleResource CreateFakeRuleResource()
  280. {
  281. return new RuleResource()
  282. {
  283. Id = "/subscriptions/a93fb07c-6c93-40be-bf3b-4f0deba10f4b/resourceGroups/Default-Web-EastUS/providers/microsoft.insights/alertrules/checkrule3-4b135401-a30c-4224-ae21-fa53a5bd253d",
  284. Name = Name,
  285. Properties = new Rule()
  286. {
  287. Actions = new BindingList<RuleAction>()
  288. {
  289. new RuleEmailAction(),
  290. },
  291. Condition = new ThresholdRuleCondition()
  292. {
  293. DataSource = new RuleMetricDataSource()
  294. {
  295. MetricName = "CpuTime",
  296. ResourceUri = ResourceUri,
  297. },
  298. Operator = ConditionOperator.GreaterThan,
  299. Threshold = 3,
  300. TimeAggregation = TimeAggregationOperator.Total,
  301. WindowSize = TimeSpan.FromMinutes(5),
  302. },
  303. Description = null,
  304. IsEnabled = true,
  305. LastUpdatedTime = DateTime.Parse("2015-02-05T03:48:11.1426304Z"),
  306. Name = Name,
  307. },
  308. Tags = new Dictionary<string, string>()
  309. {
  310. {"$type", "Microsoft.WindowsAzure.Management.Common.Storage.CasePreservedDictionary,Microsoft.WindowsAzure.Management.Common.Storage"},
  311. {"hidden-link:/subscriptions/a93fb07c-6c93-40be-bf3b-4f0deba10f4b/resourceGroups/Default-Web-EastUS/providers/microsoft.web/sites/garyyang1","Resource"}
  312. },
  313. Location = "East US",
  314. };
  315. }
  316. public static RuleListResponse InitializeRuleListResponse()
  317. {
  318. // This is effectively testing the conversion EventData -> PSEventData internally in the execution of the cmdlet
  319. RuleResource ruleResource = Utilities.CreateFakeRuleResource();
  320. return new RuleListResponse()
  321. {
  322. RuleResourceCollection = new RuleResourceCollection()
  323. {
  324. Value = new List<RuleResource>() { ruleResource },
  325. },
  326. RequestId = Guid.NewGuid().ToString(),
  327. StatusCode = HttpStatusCode.OK
  328. };
  329. }
  330. public static RuleGetResponse InitializeRuleGetResponse()
  331. {
  332. // This is effectively testing the conversion EventData -> PSEventData internally in the execution of the cmdlet
  333. RuleResource ruleResource = Utilities.CreateFakeRuleResource();
  334. return new RuleGetResponse()
  335. {
  336. Id = ruleResource.Id,
  337. Location = ruleResource.Location,
  338. Name = ruleResource.Name,
  339. Properties = ruleResource.Properties,
  340. Tags = ruleResource.Tags,
  341. RequestId = Guid.NewGuid().ToString(),
  342. StatusCode = HttpStatusCode.OK
  343. };
  344. }
  345. public static void VerifyDetailedOutput(GetAzureRmAlertRuleCommand cmdlet, string expectedResourceGroup, ref string resourceGroup, ref string nameOrTargetUri)
  346. {
  347. // Calling with detailed output
  348. cmdlet.DetailedOutput = true;
  349. cmdlet.Name = null;
  350. cmdlet.TargetResourceId = ResourceUri;
  351. cmdlet.ExecuteCmdlet();
  352. Assert.Equal(expectedResourceGroup, resourceGroup);
  353. Assert.Equal(ResourceUri, nameOrTargetUri);
  354. }
  355. public static void VerifyFieldAndValueInCall(string filter, string filedName, string fieldValue)
  356. {
  357. VerifyFilterIsUsable(filter: filter);
  358. VerifyConditionInFilter(filter: filter, field: filedName, value: fieldValue);
  359. }
  360. public static void ExecuteVerifications(ManagementCmdletBase cmdlet, string expectedResourceGroup, ref string resourceGroup, ref string nameOrTargetUri)
  361. {
  362. // Calling without optional parameters
  363. cmdlet.ExecuteCmdlet();
  364. VerifyFilterIsUsable(filter: resourceGroup);
  365. Assert.Equal(expectedResourceGroup, resourceGroup);
  366. Assert.Null(nameOrTargetUri);
  367. var typedCmdlet = cmdlet as GetAzureRmAlertRuleCommand;
  368. if (typedCmdlet != null)
  369. {
  370. // Calling with Name
  371. typedCmdlet.Name = Name;
  372. typedCmdlet.ExecuteCmdlet();
  373. Assert.Equal(expectedResourceGroup, resourceGroup);
  374. Assert.Equal(Name, nameOrTargetUri);
  375. // Calling with ResourceUri
  376. typedCmdlet.Name = null;
  377. typedCmdlet.TargetResourceId = ResourceUri;
  378. typedCmdlet.ExecuteCmdlet();
  379. Assert.Equal(expectedResourceGroup, resourceGroup);
  380. Assert.Equal(ResourceUri, nameOrTargetUri);
  381. // Calling with Detailed ouput and resourceuri
  382. VerifyDetailedOutput(cmdlet: typedCmdlet, expectedResourceGroup: expectedResourceGroup, resourceGroup: ref resourceGroup, nameOrTargetUri: ref nameOrTargetUri);
  383. }
  384. }
  385. #endregion
  386. }
  387. }