public async Task<List<Tariff>> Estimate(Parcel parcel, DeliveryOptions deliveryOptionsoptions, CancellationToken ct)
		{
			await _browser.ExecuteJs(JsCode, ct);
			var tariffs = new List<Tariff>();

			var deliveryPath = await SetDeliveryPath(parcel, ct);
			if (string.IsNullOrWhiteSpace(deliveryPath))
				return tariffs;

			await SetParcelProperties(parcel, ct);

			if (!await _browser.Select("#calc_calculate_btn", ct))
				throw new InvalidOperationException("Can't find calculate button");
			_browser.Click();

			if (!await _browser.WaitForAjax(5000, ct))
				throw new TimeoutException("Failed to wait for cost calculation");

			await _browser.ExecuteJs(JsCode, ct);
			var itariffs = (await _browser.ExecuteJs("return fragma.modules.dpdTariffs.getTariffs()", ct) as IList);
			foreach (dynamic itariff in itariffs)
			{
				var dict = itariff as Dictionary<string, object>;
				var serviceName = dict["serviceName"].ToString();
				var cost = dict["cost"].ToString();
				var tariff = new Tariff
				{
					ProviderType = TariffProviderType.DPD,
					SubProviderName = serviceName,
					DeliveryMethod = DeliveryMethod.ToDoor,
					DeliveryPath = deliveryPath,
					Price = decimal.Parse(cost, CultureInfo.InvariantCulture)
				};
				var days = dict["days"].ToString();
				var times = days.Split('-');
				var min = TimeSpan.Zero;
				min = new TimeSpan(int.Parse(times[0].Trim()), 0, 0, 0);
				var max = min;
				if (times.Count() > 1)
					max = new TimeSpan(int.Parse(times[1].Trim()), 0, 0, 0);
				tariff.MinDeliveryTime = min;
				tariff.MaxDeliveryTime = max;
				tariff.DeliveryTime = max;
				tariffs.Add(tariff);
			}
			return tariffs;
		}
		private async Task<List<Tariff>> Estimate(string icn, Parcel parcel, DeliveryOptions deliveryOptionsoptions, CancellationToken ct)
		{
			var browser = _browsers[icn];
			var deliveryPath = await FillInCities(browser, parcel, ct);

			await FillInParcelProperties(browser, parcel, ct);

			await FillInExtraProperties(browser, parcel, deliveryOptionsoptions, ct);

			var tariffs = await GetTariffs(browser, ct);
			tariffs.ForEach(t =>
			{
				t.DeliveryPath = deliveryPath;
				t.Icn = icn;
			});
			return tariffs;
		}
		public Task<List<Tariff>> Estimate(Parcel parcel, DeliveryOptions deliveryOptionsoptions, CancellationToken ct)
		{
			if (parcel.Address2.IndexOf("казахстан", StringComparison.InvariantCultureIgnoreCase) >= 0)
				return Estimate(ModuleConfiguration.IcnKazakhstan, parcel, deliveryOptionsoptions, ct);

			var tasks = new List<Task<List<Tariff>>>();
			tasks.Add(Estimate(ModuleConfiguration.IcnRussia, parcel, deliveryOptionsoptions, ct));
			tasks.Add(Estimate(ModuleConfiguration.IcnNoCash, parcel, deliveryOptionsoptions, ct));

			Task.WaitAll(tasks.ToArray(), ct);
			var results = new List<Tariff>();
			foreach (var task in tasks)
			{
				if (task.Status != TaskStatus.Faulted)
					results.AddRange(task.Result);
			}
			return Task.FromResult(results);
		}
		private async Task FillInExtraProperties(IBrowser browser, Parcel parcel, DeliveryOptions options, CancellationToken ct)
		{
			var isNotified = options.IsNotifyViaSMS.GetValueOrDefault();
			var isChecked = (bool)await browser.ExecuteJs("return $(\"input[name='sms']\").is(':checked')", ct);
			if ((isChecked && !isNotified)
				|| (!isChecked && isNotified))
			{
				await browser.ExecuteJs("$(\"input[name='sms']\").click();$(\"input[name='sms_reciever']\").click();", ct);
			}
		}