/** * 2015-11-27 * Google API в случае сбоя возвращает корректный JSON, но с кодом HTTP 403, * что приводит к тому, что @see file_get_contents() не просто возвращает JSON, * а создаёт при этом warning. * Чтобы при коде 403 warning не создавался, использую ключ «ignore_errors»: * http://php.net/manual/en/context.http.php#context.http.ignore-errors * http://stackoverflow.com/a/21976746 * * Обратите внимание, что для использования @uses file_get_contents * с адресами https требуется расширение php_openssl интерпретатора PHP, * однако оно является системным требованием Magento 2: * http://devdocs.magento.com/guides/v2.0/install-gde/system-requirements.html#required-php-extensions * Поэтому мы вправе использовать здесь @uses file_get_contents * * @param $urlBase * @param array(string => string) $params [optional] * * 2016-05-31 * Стандартное время ожидание ответа сервера задаётся опцией default_socket_timeout: * http://php.net/manual/en/filesystem.configuration.php#ini.default-socket-timeout * Её значение по-умолчанию равно 60 секундам. * Конечно, при оформлении заказа негоже заставлять покупателя ждать 60 секунд * только ради узнавания его страны вызовом @see df_visitor() * Поэтому добавил возможность задавать нестандартное время ожидания ответа сервера: * http://stackoverflow.com/a/10236480 * https://amitabhkant.com/2011/08/21/using-timeouts-with-file_get_contents-in-php/ * * @param int|null $timeout [optional] * * * @return string|bool * The function returns the read data or FALSE on failure. * http://php.net/manual/function.file-get-contents.php */ function df_http_get($urlBase, array $params = [], $timeout = null) { /** @var string $url */ $url = !$params ? $urlBase : $urlBase . '?' . http_build_query($params); /** * 2016-05-31 * @uses file_get_contents() может возбудить Warning: * «failed to open stream: A connection attempt failed * because the connected party did not properly respond after a period of time, * or established connection failed because connected host has failed to respond.» */ return @file_get_contents($url, null, stream_context_create(['http' => df_clean(['ignore_errors' => true, 'timeout' => $timeout])])); }
/** @return string */ private function openTagWithAttributesAsText() { return df_cc_s($this->tag(), $this->shouldAttributesBeMultiline() ? "\n" : null, call_user_func($this->shouldAttributesBeMultiline() ? 'df_tab_multiline' : 'df_nop', implode($this->shouldAttributesBeMultiline() ? "\n" : ' ', df_clean(df_map_k(function ($name, $value) { df_param_string_not_empty($name, 0); /** * 2015-04-16 * Передавать в качестве $value массив имеет смысл, например, для атрибута «class». * * 2016-11-29 * Не использую @see df_e(), чтобы сохранить двойные кавычки (data-mage-init) * и в то же время сконвертировать одинарные * (потому что значения атрибутов мы ниже обрамляем именно одинарными). */ $value = htmlspecialchars(str_replace("'", ''', !is_array($value) ? $value : df_cc_s($value)), ENT_NOQUOTES, 'UTF-8', false); return '' === $value ? '' : "{$name}='{$value}'"; }, $this->attributes()))))); }
/** * 2016-08-10 * «groups[all_pay][groups][installment_sales][fields][plans][template][months]» => «months» * @param string $nameFull * @return string */ function df_fe_name_short($nameFull) { return df_last(df_clean(df_explode_multiple(['[', ']'], $nameFull))); }
/** * Отличается от @see df_clean() дополнительным удалением их исходного массива элементов, * чьим значением является применение @see df_cdata() к пустой строке. * Пример применения: * @used-by Df_1C_Cml2_Export_Processor_Catalog_Product::getElement_Производитель() * @param array(string => mixed) $array * @return array(string => mixed) */ function df_clean_xml(array $array) { return df_clean($array, [df_cdata('')]); }
/** * @param string $text * @return string[] */ public function parseTextarea($text) { return df_clean(df_trim(df_explode_n(df_trim($text)))); }
/** * 2016-09-01 * @param string[] $a * @return void */ public function iiaSetTRR(...$a) { $a = df_args($a); dfp_set_transaction_info($this->ii(), df_clean(['Request' => $a[0], 'Response' => $a[1]])); }
/** * 2016-12-01 * @param array(string|array(string|mixed)|null) ...$cs * @return string */ function df_db_or(...$cs) { return implode(' OR ', array_map(function ($c) { return implode(!is_array($c) ? $c : df_db_quote_into($c[0], $c[1]), ['(', ')']); }, df_clean($cs))); }
/** * 2016-08-24 * Несмотря на то, что опция @see \Df\Payment\Settings::askForBillingAddress() * стала общей для всех моих платёжных модулей, * платёжный адрес у заказа всегда присутствует, * просто при askForBillingAddress = false платёжный адрес является вырожденным: * он содержит только email покупателя. * * Только что проверил, как метод работает для анонимных покупателей. * Оказывается, если аноничный покупатель при оформлении заказа указал адреса, * то эти адреса в данном методе уже будут доступны как посредством * @see \Magento\Sales\Model\Order::getAddresses() * так и, соответственно, посредством @uses \Magento\Sales\Model\Order::getBillingAddress() * и @uses \Magento\Sales\Model\Order::getShippingAddress() * Так происходит в связи с особенностью реализации метода * @see \Magento\Sales\Model\Order::getAddresses() * https://github.com/magento/magento2/blob/2.1.0/app/code/Magento/Sales/Model/Order.php#L1957-L1969 if ($this->getData('addresses') == null) { $this->setData('addresses', $this->getAddressesCollection()->getItems()); } return $this->getData('addresses'); * Как видно, метод необязательно получает адреса из базы данных: * для анонимных покупателей (или ранее покупавших, но указавшим в этот раз новый адрес), * адреса берутся из поля «addresses». * А содержимое этого поля устанавливается методом @see \Magento\Sales\Model\Order::addAddress() * https://github.com/magento/magento2/blob/2.1.0/app/code/Magento/Sales/Model/Order.php#L1238-L1250 * * @param bool $bs * @return OA */ private function addressMixed($bs) { return dfc($this, function ($bs) { /** @var OA[] $aa */ $aa = df_clean([$this->addressB(), $this->addressS()]); $aa = $bs ? $aa : array_reverse($aa); /** @var OA $result */ $result = df_create(OA::class, df_clean(df_first($aa)->getData()) + df_last($aa)->getData()); /** * 2016-08-24 * Сам класс @see \Magento\Sales\Model\Order\Address никак order не использует. * Однако пользователи класса могут ожидать работоспособность метода * @see \Magento\Sales\Model\Order\Address::getOrder() * В частности, этого ожидает метод @see \Dfe\TwoCheckout\Address::build() */ $result->setOrder($this->o()); return $result; }, func_get_args()); }
/** * 2016-11-28 * @override * @see \Df\Sso\Button::attributes() * @used-by \Df\Sso\Button::loggedOut() * @see \Dfe\FacebookLogin\Button::attributes() * @return array(string => string) */ protected function attributes() { return df_x_magento_init_att($this, 'button', $this->jsOptions() + ['redirect' => $this->getUrl(df_route($this), df_clean(['_secure' => $this->redirectShouldBeSecure()], false)), 'type' => $this->s()->type()]) + parent::attributes(); }
/** * @see df_cc() * @param string $glue * @param string[] ...$elements * @return string */ function df_ccc($glue, ...$elements) { return implode($glue, df_clean(dfa_flatten($elements))); }
/** * 2015-10-12 * Регистрация нового клиента. * @param MC $customer * @return void */ private function register(MC $customer) { /** * 2015-10-12 * https://github.com/magento/magento2/issues/2087 * Приходится присваивать магазин в 2 шага... */ /** @var \Magento\Store\Api\Data\StoreInterface|\Magento\Store\Model\Store $store */ $store = df_store_m()->getStore(); $customer->setStore($store); $customer->setGroupId(df_customer_group_m()->getDefaultGroup($store->getId())->getId()); $customer->addData($this->customerData()); $customer->save(); /** * 2016-06-05 * Не всегда имеет смысл автоматически создавать адрес. * В частности, для Amazon решил этого не делать, * потому что автоматический адрес создаётся на основании геолокации, что не точно, * а в случае с Amazon мы гарантированно можем получить точный адрес из профиля Amazon, * поэтому нам нет никакого смысла забивать систему неточным автоматическим адресом. * @see \Dfe\AmazonLogin\Controller\Index\Index::needCreateAddress() */ if ($this->needCreateAddress()) { /** @var Address $address */ $address = df_om()->create(Address::class); $address->setCustomer($customer); $address->addData(df_clean($this->addressData() + ['firstname' => $this->c()->nameFirst(), 'lastname' => $this->c()->nameLast(), 'middlename' => $this->c()->nameMiddle(), 'city' => df_visitor()->city(), 'country_id' => df_visitor()->iso2(), 'is_default_billing' => 1, 'is_default_shipping' => 1, 'postcode' => df_visitor()->postCode() ?: (df_is_postcode_required(df_visitor()->iso2()) ? '000000' : null), 'region' => df_visitor()->regionName(), 'region_id' => null, 'save_in_address_book' => 1, 'street' => '---', 'telephone' => '000000'])); $address->save(); } df_dispatch('customer_register_success', ['account_controller' => $this, 'customer' => $customer]); }