Случайны выбор дневника Раскрыть/свернуть полный список возможностей


Найдено 2939 сообщений
Cообщения с меткой

http - Самое интересное в блогах

Следующие 30  »
rss_rss_hh_new

[Перевод] Идеальная производительность протокола HTTP

Вторник, 26 Апреля 2016 г. 14:48 (ссылка)

Один из аспектов понятия «производительность Web» заключается в том, чтобы уменьшить наблюдаемые пользователем задержки; получить готовую к работе страницу как можно быстрее. В отношении протокола HTTP это подразумевает, что идеальный протокол связи выглядит как-то так:







Клиент шлёт минимально необходимое количество данных, чтобы описать свой запрос, а сервер отдаёт ему минимально необходимое количество данных для отображения страницы и всё это происходит за минимально возможное количество раундов связи. Лишние данные, пересылаемые на сервер или получаемые с сервера, означают увеличение времени загрузки и повышение шансов потери пакетов, перегруженность канала связи. Лишние циклы отправки\приёма данных из-за «болтливости» протокола и задержки (особенно в мобильных сетях, где 100ms — лучшее возможное время отклика) тоже ухудшают ситуацию.



Итак, если мы описали идеальный случай — соответствует ли ему протокол HTTP? И можем ли мы ещё как-нибудь улучшить его?



HTTP/1.1

HTTP/1.1 это хороший протокол по целому ряду причин, но, к сожалению, производительность не одна из них по причине того, как современные веб-приложения его используют. А используют они его сегодня вот так:







Не очень-то хорошо.



Использование веб-приложениями протокола HTTP/1 достаточно «болтливо», поскольку клиент обращается к серверу снова и снова для загрузки необходимых ему файлов; сначала загружается HTML, затем CSS и Javascript. Загрузка каждого следующего файла добавляем в наш «разговор» с сервером новую главу, увеличивает общую задержку загрузки страницы, нарушая наше правило «минимальности необходимых раундов связи».



Более того, даже сами запросы к ресурсам уже добавляют много лишних данных, нарушая правило «минимальности необходимых данных». Это происходит из-за наличия заголовков вроде Referer, User-Agent и, конечно же, Cookie, которые повторяются в каждом запросе, умножаясь иногда в сотню раз от минимально необходимого их количества (по количеству ресурсов, необходимых средней страницей современного Веба).



Ну и наконец, из-за присущего протоколу HTTP/1 явлению HOL-блокировки, стало общей практикой помещать несколько отдельных ресурсов в один (например, CSS spriting). Все эти изящные хаки протокола HTTP/1, тем не менее, имеют свою цену; они вынуждают клиента загружать больше данных, чем ему необходимо в данный момент для показа конкретной страницы, что нарушает описанный нами идеальный случай, а значит мы не покажем страницу так быстро, как это только возможно.



Несмотря на всё сказанное, HTTP/1.1 всё же не так плох, даже в плане производительности. Например, в нём есть кеширование, что избавляет вас от повторной загрузки неизменённых ресурсов, а также условные запросы, что позволяет вам понять, нужно ли загружать новую версию файла.



HTTP/2



Протокол HTTP/2 пытается решать проблемы 1.1 несколькими путями:




  1. Полное мультиплексирование означает решение проблемы HOL-блокировки. Вы можете загружать все ресурсы своей страницы по одному HTTP-соединению и не волноваться о том, сколько для этого понадобится сделать запросов. «Оптимизации» со склеиванием файлов в один можно оставить в прошлом.

  2. Сжатие заголовков решает проблему их избыточности. Теперь вы можете вместить десятки (или даже сотни) запросов в буквально несколько IP-пакетов. Это серьёзно приближает нас к «минимально необходимому набору данных» нашего идеального протокола.

  3. HTTP/2 позволяет серверу отправлять данные клиенту ещё до их запроса клиентом, исходя из предположения, что они ему скоро понадобятся. Это уменьшает количество раундов связи клиента и сервера.





Таким образом, сеанс связи с использованием протокола HTTP/2 выглядит как-то так:







Здесь вы можете увидеть, как сервер начинает пересылку CSS и Javascript клиенту ещё до того, как клиент об этом попросил. Сервер знает, что клиент, запросивший HTML, с большой вероятностью запросит и относящиеся к нему CSS и Javascript файлы, а значит можно отправить их, не дожидаясь самого запроса. Таким образом, мы теряем меньше времени на ожидание, используем сеть более рационально.



Следует отметить, всё это работает не так уж просто. До сих пор в HTTP/2 есть открытые вопросы, касающиеся того, что и когда сервер должен считать необходимым к отправке без запроса клиента.



HTTP/2 + дайджесты кеша

Хороший вопрос, касающийся инициированной сервером пересылки файлов: «А что, если у клиента уже есть его копия в кеше?». Действительно, было бы глупо насильно отправлять клиенту что-то, что у него уже есть.



HTTP/2 позволяет клиенту в этом случае досрочно завершить загрузку такого ресурса, с помощью сообщения RESET_STREAM. Но даже в этом случае у нас гоняются лишние данные, добавляется ещё один раунд связи, чего хотелось бы избежать. Вы помните правило из первого абзаца статьи: «пересылать лишь минимально необходимое количество данных для отображения страницы».



Предлагаемое решение проблемы — дать клиенту возможность сформировать компактный дайджест кеша и переслать его серверу, чтобы тот знал, какие ресурсы клиенту точно не нужны.







Поскольку дайджесты кеша используют коды Голомба, реально предположить, что для среднего размера страницы браузеру понадобится менее 1000 байт, чтобы объяснить серверу, какие ресурсы есть у него в кеше.



Теперь мы действительно избегаем лишних циклов связи клиента и сервера, передачи лишних данных, склейки нескольких файлов в один и похожих хаков, а также неэффективной пересылки ненужных нам данных. Это очень существенно приближает нас к идеалу!



Дайджесты кеша пока только предложение к расширению протокола, но к ним существует большой интерес у HTTP-сообщества. Мы обязательно увидим и оценим их использование уже в самом ближайшем будущем.



TCP

Давайте поговорим о влиянии на общую производительность других протоколов, используемых браузером для загрузки страниц. А оно тоже может быть существенным: TCP использует троекратное рукопожатие ещё до того, как первый байт стоящего выше HTTP будет переслан:







Это добавляет «болтливости» каждому сеансу связи. TCP Fast Open позволяет приложениям отправлять данные прямо в SYN и SYN+ACK пакетах. К сожалению, это в данный момент поддерживается только в Linux и OSX, и более того, есть некоторые особенности применения TCP Fast Open именно с протоколом HTTP, над которыми сейчас работает сообщество. Например, не гарантируется, что данные, прикреплённые к SYN-пакету, будут пересланы лишь один раз. Это открывает уязвимость с потенциальными повторными запросами, которая может быть использована для атак. Таким образом, запрос POST — не лучший кандидат для применения TCP Fast Open. Более того, некоторые GET-запросы тоже имеют заметные побочные эффекты, а браузеры не имеют никаких средств, чтобы отличить такие запросы от тех, которые таких эффектов не имеют.



TLS

TLS добавляет ещё один уровень взаимодействия клиента и сервера, уже после того, как TCP соединение было установлено. Это выглядит вот так:







Это два полных цикла обмена сообщениями перед тем, как протокол HTTP отправит свой первый запрос; достаточно разговорчиво, не правда ли? Если клиент и сервер уже общались раньше, мы можем несколько сократить общение:







Вскоре TLS 1.3 позволит достичь «нулевого» рукопожатия для случая, когда клиент и сервер уже общались ранее — иными словами протокол HTTP получить возможность добавить полезную нагрузку уже в первый отправленный на сервер пакет данных. Но так же, как и с TCP Fast Open, понадобиться некоторое решение для избегания дублирования запросов.



HTTP/next

TCP Fast Open и TLS 1.3 уменьшают количество циклов связи клиента и сервера при открытии соединения. Другой способ достичь того же — переиспользовать уже ранее открытое соединение. Сейчас идёт дискуссия о том, как объединять соединения HTTP/2 более агрессивно; это позволит не только избежать затрат на открытие новых соединений, но и более эффективно использовать уже имеющиеся — протокол TCP наиболее хорош именно в долгоживущих, плотно заполненных данными соединениях. Это включает в себя отправку клиенту сертификатов, доказывающих, что соединение может быть безопасно переиспользовано для работы с другими источниками.



Сейчас обсуждаются даже более кардинальные эксперименты: замена TCP на UDP, навроде QUIC. Есть много спорных моментов, но сама перспектива свести начальный обмен данным фактически до нуля — очень привлекательна. Более того, возможность получить доступ к данным не в том порядке, как они были отправлены, тоже может быть очень полезна. Это ещё один способ избежать HOL-блокировок в TCP (протоколе с упорядоченной доставкой пакетов). Мы можем выбрать из потока пакетов нужные нам, понять, что какие-то были потеряны, запросить их повторно — и продолжить обработку следующих, не дожидаясь результатов повторного запроса.



QUIC только начинает свой путь, так что мы ещё не увидим хорошей его реализации какое-то время (а может быть и никогда вообще). Один из возможных вариантов — изучить на примере QUIC все плюсы и минусы подхода, чтобы понять, как мы можем улучшить производительность TCP, не ударяясь в столь кардинальные изменения архитектуры Web.

Original source: habrahabr.ru (comments, light).

https://habrahabr.ru/post/282517/

Метки:   Комментарии (0)КомментироватьВ цитатник или сообщество
rss_rss_hh_new

[Из песочницы] Разработка webApi модуля для Angular.js

Понедельник, 25 Апреля 2016 г. 13:40 (ссылка)

Желание разработать собственный Angular.js webApi модуль возникло при работе с большим количеством http-запросов в проекте.


Важно было не просто создать файл с константами, а разработать некий модуль для упрощения поддержки существующего функционала. В свою очередь, необходимо было и позаботиться о возможном последующем расширении без нарушения целостности текущего ядра модуля.



Задачи, которые должен решать будущий webApi модуль:




  1. Предотвратить дублирование http-запросов в проекте.

  2. Группировать существующий список запросов по функциональным категориям, чтобы проще вносить правки в конкретные методы.

  3. Быть полностью независимой функциональной единицей приложения, которая подключается к любому другому Angular.js проекту простым Dependency Injection'ом.

  4. Инкапсулировать внутреннюю реализацию, чтобы избежать проблем при работе с внешними источниками.



Дальше поговорим о каждом из этих пунктов подробнее.



Дублирование http-запросов



Речь идет об использовании одного запроса в нескольких местах приложения (контроллеры, сервисы, фабрики). Когда методов 10-20, то внести изменения в каждый запрос не составит большой проблемы. Но когда речь идет о количестве 100, 200 и более url'ов, поддержка такого кода вызывает все больше трудностей.



Пример #1



Есть метод, который получает список групп пользователей. Допустим, он выводится в соответствующий dropdown. При выборе группы происходит подгрузка ее юзеров по другому запросу, куда передается "id" группы. Также на странице имеется дополнительный функционал для визуализации каких-то данных пользователей.



// получаем все группы
$http.get("api/group-manage/get-all")

// получаем пользователей выбранной группы
$http.get("api/group-manage/2/get-users")


В другом контроллере есть таблица, где нужно вывести всех пользователей системы по конкретной группе. Эта страница предоставляет значительно больше возможностей для анализа и менеджмента пользователей.



// получаем пользователей выбранной группы
$http.get("api/group-manage/2/get-users")


В действительности похожих запросов может быть значительно больше.



Решение проблемы



Создать специальный файл с константами, содержащий список всех http-запросов на сервер, т.е. всех используемых в приложении url'ов. 


Данный подход позволит сэкономить время при поиске необходимого запроса в проекте и его модификации.



Опять же, работать с таким файлом получится только при наличии небольшого количества запросов к серверу. Трудно себе представить удобную поддержку файла с константами, которых более 200.



Группировать запросы по категориям



Этот подход позволит решить вытекающую выше проблему. Как именно будет происходить определение независимых категорий — определяет сам разработчик. Для простоты можно ориентироваться на имя контроллера-метода из api.



// http://yourapi.com/api/group-manage/2/get-users
// http://yourapi.com/api/group-manage/get-all


Из примера выше видно, что в запросах есть общий корень /api/group-manage/. Создаем категорию с соответствующим названием groupManage.js.



В Angular.js среде данный файл объявляется как constant, который в дальнейшем подключается к основному функционалу webApi модуля.


Таких групп в проекте может быть несколько. Но теперь мы определенно знаем где искать запросы, относящиеся к менеджменту групп.



Если же вызывать добавленный url напрямую, то рано или поздно появится череда однотипных зависимостей в коде. Поэтому, необходимо создать общий блок, предоставляющий список всех существующих запросов для оперирования ими в "ядре" webApi.



Инкапсуляция функционала



Одной из самых сложных задач была разработка ядра, которое сможет оперировать всеми запросами к серверу, при этом не только не раскрывать свою внутреннюю реализацию, но и предоставлять возможность легкого конфигурирования webApi модуля под конкретное Angular.js приложение.



Пример запроса выглядит следующим образом:



{ Url: '/api/acc/login', CustomOptions: false, Method: 'post', InvokeName: 'login' }



  • customOptions — использовать ли дополнительные настройки запроса. Обычно там могут указываться header'ы для конкретного запроса, значение timeout, параметр withCredentials и др.



Такой подход позволяет не только группировать несколько url по общему типу, но еще и иметь представление, что каждый метод будет делать с данными.



В директории webApi/config/ находится файл с настройками API. Именно там мы и указываем DOMAIN url.



Пример #2



Практически все современные Angular.js приложения работают с системой аутентификации. Обычно это post-метод, который отправляет на сервер данные юзера (login, password).



При успешном respons'e происходит оповещение главному роуту приложения, после чего пользователь будет перенаправляется на страницу с функционалом.



Вызываем метод:



webApi.login({
"Login": "user",
"Password": "qwerty"
}).success(function(response, status, headers, config){
// какие-то действия
})


Таким образом, мы работаем на специальном уровне абстракций, что позволяет сосредоточиться на процессе построения логики приложения. Желательно давать адекватные наименования методам, чтобы можно было понять, что делает конкретный вызов:



// объявляем запрос в настройках
{ Url: '/api/acc/logout', CustomOptions: false, Method: 'get', InvokeName: 'logout' }

// где-то вызываем метод
webApi.logout([]);


Наверное, сейчас не совсем понятно использование пустого массива в get-методе, но дальше об этом всем будет рассказано.



Шаблонизация запросов



Довольно часто при разработке приложения, сервер-сайд предоставляет клиенту следующий формат запросов:




  • /api/admin/delete/profile/{id}

  • /api/admin/update/profile/{id}/block



И чтобы в при отправке запроса на сервер в нужном месте приложения не производить лишних операций с построением такого url, был разработан специальный компонент, автоматически генерирующий правильный адрес на основе полученных параметров.



// объявляем запрос в настройках
{ Url: '/api/admin/update/profile/{id}/block', CustomOptions: false, Method: 'put', InvokeName: 'blockAdminProfileById' }

// где-то вызываем метод
webApi.blockAdminProfileById({
"url": { "id": 5 }
});


Сгенерированный запрос: /api/admin/update/profile/5/block (плюс domain url, разумеется).



И если нам нужно отправить на сервер более сложный запрос (например, длительность блокировки и тип), то просто указываем остальные параметры в качестве полей объекта "url":



// объявляем запрос в настройках
{ Url: '/api/admin/update/profile/{id}/block/{type}/{time}', CustomOptions: false, Method: 'put', InvokeName: 'blockAdminProfileById' }

// где-то вызываем метод
webApi.blockAdminProfileById({
"url": {
"id": 5,
"type": "week",
"time": 2
}
});


Сгенерированный запрос: /api/admin/update/profile/5/block/week/2. И теперь пользователь будет заблокирован системой на 2 недели.



Шаблонизация работает для всех типов запросов, включая get. Желательно все запросы формировать именно таким образом: экономим время, не засоряем внутренний код лишними операциями.



Передача данных в теле запроса



Следует отметить, что если Вы хотите отправить помимо шаблонизированного url на сервер еще и какие-то данные (например, post-запрос), то необходимо их передать следующим образом:



webApi.createPost({
"data": {
"title": "Test post",
"category": "sport",
"message": "Content..."
}
});


Естественно, можно использовать одновременно и url-шаблонизацию, и передачу объекта с данными. Последний будет отправлен на сервер в теле запроса.



Работа с GET-методами



Тут никакие данные в теле запроса не передаются, но всем известно, что get-запрос может быть сформирован так:



api/admin/news/10?category=sport&period=week



или так:



api/admin/manage/get-statistic/5/2016



или же так:



api/admin/manage/get-all.



Рассмотрим каждый из вариантов генерации.



Примеры создания get-запроса
// Case #1 -> api/admin/manage/get-all
// в настройках -> "Url" : 'api/admin/manage/get-all', ...
// вызываем метод
webApi.getAllAdmins([]).success(//...)

// Case #2 -> api/admin/manage/get-statistic/5/2016
// в настройках -> "Url" : 'api/admin/manage/get-statistic/{id}/{year}', ...
// вызываем метод
webApi.getAdminStatsticById({
"url": {
"id": 5,
"year": 2016
}
}).success(//...)

// Case #3 -> admin/news/10?category=sport&period=week
// в настройках -> "Url" : 'admin/news', ...
// вызываем метод
webApi.getNews({
before: ['10'],
after: {
"category": "sport",
"period": "week"
}
}).success(//...)


Со вторым типом запросов мы уже разобрались выше.



В первом же случае мы всегда передаем пустую коллекцию, когда нужно просто отправить запрос на сервер.



В случае #3 поле before определяет ряд параметров, которые идут до знака "?", а поле after — набор "ключ-значение". Естественно, в некоторых случаях можно оставить before пустой коллекцией [].



Параметр CustomOptions в настройках



Get-запрос без шаблонизации url:



webApi.getNewsById([10, {"headers": {"Content-Type": "text/plain"} } ]);


Во всех остальных случаях (в том числе, get-запросы с шаблонизацией url):



webApi.login({
options: {"timeout": 100, {"headers": {"Content-Type": "text/plain"} }
});


Настройка webApi в новом проекте



Структура модуля следующая:




  • файл module.js — объявление самого модуля;

  • директория main/ — содержит в себе ядро webApi, оно не изменяется;

  • директория categories — группы запросов, одна группа — один *.js файл;

  • директория categories-handler — регистратор всех запросов в webApi модуле.



Вам придется работать с последними двумя директориями.



Пример #3



Допустим, разрабатывается система учета книг в каком-то университете. Большая вероятность разбиения запросов на следующие группы:




  • account.js — запросы на авторизацию, деавторизацию, восстановление паролей и т.д.;

  • bookManage.js — запросы на CRUD-операции с книгами;

  • studentManage.js — менеджмент студентов;

  • adminManage.js — ряд запросов по управление админской частью приложения.



Конечно, этот список может быть расширен.



Главное - стараться максимально четко группировать запросы, чтобы потом легко было добавлять новые методы и редактировать существующие.


Объявляем новую категорию запросов
(function(){

angular
.module("_webApi_")
.constant("cat.account", {

"DATA": [

{ Url: '/api/acc/login', CustomOptions: false, Method: 'post', InvokeName: 'login' },
// остальные запросы

]

});

})();


Файл с запросами создан. Теперь нужно связать его с нашим webApi ядром.



Добавляем группу запросов в специальный обработчик
(function(){

angular
.module("_webApi_")
.service("webApi.requests", webApiRequests);

function webApiRequests(catAccount){

// специальные обработчики и регистраторы
// их изменять не нужно, только добавляем новые зависимости

}

// IoC container.
webApiRequests.$inject = [
"cat.account"
];

})();


В данном случае все константы пишутся через "cat.имя константы", а подключаются в регистратор "catИмяКонстанты".



Таким образом, в webApi используется дополнительное пространство имен "cat.", чтобы не было конфликтов с другими константами в приложении.



И теперь вызываем метод согласно описанному шаблону:



webApi.login( //логин-пароль для авторизации )



Заключение



Мы рассмотрели вариант создания конфигурируемого и расширяемого webApi модуля для работы с Angular.js.



Данный подход поможет вам избавиться от дублирования логики в коде, сократить время на редактирование необходимого метода, а также облегчить работу со сложными запросами.



Demo



Посмотреть исходный код модуля: github.



Original source: habrahabr.ru (comments, light).

https://habrahabr.ru/post/282397/

Метки:   Комментарии (0)КомментироватьВ цитатник или сообщество
rss_rss_hh_new

За что могут высечь плетьми в цифровую эпоху? Как GitHub соблюдает DMCA, RFC 7725 и что за HTTP 451?

Суббота, 19 Марта 2016 г. 04:10 (ссылка)

В далёком 2012 на Хабре обсуждались «рестриктеры», «делитеры», «цензурасты», а также «абузо-устойчивые» провайдеры в статье про то, что был предложен новый HTTP-статус для цензуры, а точнее для ресурсов, доступ к которым ограничен из-за проблем с законом.



Собственно статус HTTP 451 был предложен Тимом Брэйем из Google, а виновником (в прямом и переносном смысле) переполоха стал в очередной раз заблокированный, заабузенный, зацензуренный и великий The Pirate Bay.



Почему это важно? Потому что вы, наверное, как и я, пользуетесь GitHub, программируете не только для души и, возможно, владеете доходными интернет-ресурсами.



Вы уже находитесь в правовом поле авторского права.



На написание этого поста, первого за 2 года молчания на Хабре, меня подтолкнула история, которая произошла недавно со мной. Если интересно, она внизу поста, а сейчас про RFC 7725, GitHub и DMCA.



451 Unavailable For Legal Reasons



Совсем недавно, в феврале этого года, вышеупомянутое предложение сотрудника Google было ратифицировано IETF в виде стандарта RFC 7725 Status Code to Report Legal Obstacles (пер. код состояния, сообщающий о юридических ограничениях).



Это означает, что в недалёком будущем интернет-провайдеры, хостинги, поисковики и различные сервисы станут показывать грустную «ошибку» 451 Unavailable For Legal Reasons вместо 404 Not Found, 403 Forbidden и вместо того, что первое пришло в голову, при попытке доступа к интернет-ресурсам, на которых возложены законом ограничения.



GitHub уже поддерживает



Буквально позавчера в блоге GitHub появилась заметка о том, что GitHub теперь поддерживает RFC 7725.



Наряду с упоминанием этого RFC, в посте указано как правильно посылать в GitHub претензии о нарушениях авторского права, и о том, как GitHub выполняет требования DMCA.



Что сказано в RFC 7725?
Как указано в спецификации, этот код состояния может быть использован для обеспечения прозрачности в условиях, когда вопросы права или государственной политики влияют на работу сервера, и что такая прозрачность может быть полезна как операторам, так и конечным пользователям.



HTTP-ответ с кодом 451 по-умолчанию является кешируемым, если не указаны другие HTTP-заголовки, влияющие на кеширование запроса.



Сервер, отвечающий на запрос может не не быть конечным сервером. Такой тип юридических ограничений связан с работой интернет-провайдеров и поисковых машин.



Кроме того, говорится, что ответ должен содержать разъяснение в теле HTTP-ответа с подробностями наложенного ограничения: лицо возлагающее такие ограничения, основание для наложения ограничения, и по отношению к каким лицам такое ограничение действительно.



Также в заголовке Link HTTP-ответа должен содержатся URI того сервера, который блокировал доступ к исходному ресурсу.



Ответ с HTTP статусом 451 не говорит о наличии или отсутствии ресурса, а лишь указывает на наличие ограничений.



Из соображений безопасности, клиент не должен полагаться на ответ 451, т.к. возможна ситуация, когда некоторый юридический орган захочет не только потребовать ограничение доступа, но и скрыть причастность к наложению ограничений.



А DMCA это что?
DMCA это закон США об авторском праве в цифровую эпоху. Почему не просто авторское право? Потому что изначально авторское право США описывало различные правовые отношения в сфере производства и распространения литературы, музыки, фильмов и никак не учитывало появление и развитие цифровых технологий, которые создают определенные сложности в применении и использовании авторского права «как есть» без учёта особенностей цифровых технологий.





GitHub соблюдает DMCA



Оказывается, у GitHub есть свой репозиторий, содержащий тексты обращений правообладателей к GitHub. Этот репозиторий содержит по сути конкретные прецеденты (1139 на данный момент), конкретные ситуации, с которыми можно столкнуться, публикуя свой код в GitHub, используя чей-то исходный код без сохранения надлежащих лицензионных приписок или грубо нарушая права авторов.



Среди юридических органов, которые обращались к GitHub с просьбой заблокировать доступ к чьему-то репозиторию всплывают такие организации: Oracle, Cisco, Sony, Nintendo, Instagram, Microsoft, Apple, Adobe Systems, IEEE.



Выводы



Настало время, когда задумываться о DMCA, вместо того чтобы нести людям свет, приходится чаще, чем делать своё дело.



К примеру, сайт безобидного приложения GBA4iOS (эмулятор GameBoy Advance для iPhone), который использовал GitHub в качестве хостинга был удален по требованию Nintendo Of USA.



Если вы вдруг «расковыряете» чьё-то популярное мобильное приложение про фотографии и используете например шейдеры из него, а потом выложите свой проект на GitHub, вас могут высечь плетьми.



Не пытайтесь переименовать имена методов или классов в чьем-то исходном коде, чтобы «замазать» авторство, вас обязательно вычислят и заточат в темницу.



Не вздумайте удалять портянку комментариев с какими-то словами про MIT License, даже если работаете над форком BitCoin, вас могут закопать по шею в песок.



Ну вы поняли, ещё около 1135 примеров плохих идей.



Что же делать?





Я не хочу нарушать авторские права

  1. Уточняйте под какой лицензией находится код, который вы используете

  2. Общайтесь с автором исходного кода по e-mail и потребуйте либо добавить атрибуцию желаемой лицензии, либо разрешение автора на использование его кода

  3. Если вы не можете получить никакого ответа от автора по e-mail, напишите ему в Твиттере о том что отправили письмо

  4. Читайте новости об авторском праве, изучайте прецеденты и право

  5. Попробуйте проще относиться к жизни





Я нарушаю авторские права

  1. Не стоит об этом рассказывать всем и каждому

  2. Попробуйте перестать нарушать хотя бы какие-то права, следуя разделу «Я не хочу нарушать чужие права»

  3. Примите себя таким, какой вы есть

  4. Заранее найдите лучшего адвоката, узнайте его стоимость





Мои права нарушили

  1. Вы оскорблены или же несёте материальные убытки?

  2. Обратитесь в GitHub, следуя соответствующей инструкции, и не забудьте добавить эти формальности

  3. Предпримите действия, чтобы другие не могли последовать примеру и нарушить ваши права

  4. Может стоит задуматься о том, чтобы сделать вашу работу достоянием общественности?

  5. Попробуйте оформить иск нарушающей стороне

  6. Смиритесь с несправедливостью этого мира и расскажите о вашем опыте







Надеюсь эти замечательные советы помогут вам! Благодарю за прочтение моего поста!

Поделитесь этим постом с другом, зависающим на GitHub.



Бонусы прочитавшим



История о GitHub Gist, Stackoverflow и MediaWiki
Как-то в треде на Stackoverflow я опубликовал небольшой сниппет и выложил его в GitHub с помощью сервиса Gist.



Мой gist стал пользоваться определенной популярностью, и неожиданно для себя я получил сообщение от некоего FlorianSW, который занимается разработкой расширения для MediaWiki. Сообщение содержало просьбу добавить к сниппету открытую лицензию, т.к. это позволит ему спокойно использовать этот сниппет в своём проекте.



Не особо задумываясь, я, решив сделать доброе дело, просто добавил лицензию MIT к сниппету, т.к. это одна из самых свободных лицензий. К тому же она совместима с GPLv2. Меня возмутило и насторожило то, что вроде бы я и опубликовал свой сниппет в открытом доступе, но почему-то просто взять и модифицировать или использовать его для кого-то неприемлимо из-за DMCA.



Позже, я конечно же понял, что автора возможно насторожило, что контент на Stackoverflow публикуется под CC BY-SA 3.0 и якобы мой сниппет также мог подпадать под действие этой лицензии.



… А осадок остался.







Original source: habrahabr.ru (comments, light).

https://habrahabr.ru/post/279639/

Метки:   Комментарии (0)КомментироватьВ цитатник или сообщество
rss_rss_hh_new

HTTP/2: готовимся к переходу

Вторник, 01 Марта 2016 г. 11:03 (ссылка)

HTTP/2



В прошлом году в мире сетевых технологий произошло очень важное событие: была утверждена и стандартизирована новая версия протокола HTTP — HTTP/2. HTTP/2 уже поддерживается в популярных веб-серверах: Apache и Nginx. Идёт работа по внедрению HTTP/2 в IIS. Реализована поддержка и в большинстве современных браузеров.



Использование HTTP/2 за последнее время существенно расширилось.





По данным на середину 2015 года, процент сайтов и веб-сервисов, перешедших на HTTP/2, был невелик - всего 0,4%. Совсем свежая статистика (январь 2016) свидетельствует о значительном росте: с 0,4 до 6,5%. Есть все основания полагать, что в ближайшее время темпы роста будут увеличиваться.



Задуматься о практических аспектах перехода на HTTP/2 стоит уже сейчас. Эту тему мы хотели бы затронуть в сегодняшней статье. Особенно нас будет интересовать проблема адаптации существующих приёмов оптимизации производительности веб-сайтов под специфику нового протокола.

Прежде чем перейти непосредственно к рассмотрению этого вопроса, обратимся к истории протокола HTTP/2 и кратко опишем основные нововведения, отличающие его от HTTP/1.1.



От HTTP к HTTP/2





Немного истории





Первое описание протокола HTTP (HyperText Transfer Protocol) было опубликовано в 1991 году. В 1999 году была разработана и описана версия HTTP 1.1, используемая и по сей день. В то далёкое время (почти 20 лет назад) веб-сайты были совсем не такими, как сейчас. За относительно небольшой период времени сайты стали «весить» гораздо больше. Домашняя страница среднестатического современного сайта содержит примерно 1,9 МБ данных: изображения, JS, CSS и многое другое.



Из-за ограничения на количество одновременных подключений в HTTP/1.1 загрузка страниц, содержащих большое количество «тяжёлого» контента, осуществляется медленно. Можно выделить два пути решения этой проблемы. Первый заключается в использовании различных техник оптимизации производительности (о некоторых из них мы уже писали), а второй — в попытке модификации самого протокола HTTP с целью устранения возможных узких мест. Рассмотрим такие попытки более подробно.



Первый масштабный проект реформирования HTTP был представлен в 2009 году инженерами Google. Это протокол SPDY, целью которого в первую очередь было ускорение работы веб-сайтов и приложений путём модификации традиционных способов приёма и отправки запросов.



SPDY требует поддержки как на стороне сервера, так и на стороне клиента. Разработчики Google создали специализированные модули для Apache (mod_spdy) и для Nginx (ngx_http_spdy_module). Поддерживается он и практически во всех популярных браузерах.



HTTP/2, представленный шестью годами позже, во многом основывается на SPDY. Новая версия HTTP была создана рабочей группой Hypertext Transfer Protocol working group. В мае 2015 года специкация HTTP/2 была опубликована как RFC 7540.



Протокол HTTP/2 обратно совместим с HTTP/1.1. Изменения, направленные на устранение узких мест и повышения производительности, во многом продолжают линию SPDY. Рассмотрим вкратце наиболее важные из них.



HTTP/2: основные нововведения





Мультиплексирование





Возможно, это самое главное преимущество HTTP/2. В HTTP/1.1 для каждого запроса требуется устанавливать отдельное TCP-соединение. Мультиплексирование же позволяет браузеру выполнять множество запросов в рамках одного TCP-соединения:



HTTP/2



В современных браузерах количество одновременных TCP-соединений ограничено. Поэтому страницы с большим количеством статического контента загружаются не так быстро, как хотелось бы.



В HTTP/2 благодаря мультиплексированию статические элементы загружаются параллельно, и благодаря этому существенно улучшается производительность.



Приоритеты





Ещё одно нововведение HTTP/2 — это приоритизация. Каждому запросу можно назначить приоритет.

Существует два подхода к назначению приоритетов: на основе веса и на основе зависимостей.



В первом подходе каждый поток получает определённый вес. Потом на основе веса сервер распределяет нагрузку между потоками. Такой подход уже использовался в протоколе SPDY.



Второй метод, являющийся основным в HTTP/2, заключается в следующем: браузер просит сервер загружать определённые элементы контента в первую очередь. Например, сначала браузер может попросить сервер сначала загрузить CSS-файлы или JavaScript, а уже потом — HTML или изображения.



В HTTP/2 приоритизация является не обязательным, а желательным методом. Однако мультиплексирование без неё работать должным образом не будет. Скорость загрузки может быть даже ниже, чем HTTP/1.1. Ресурсы с более низким приоритетом будут занимать полосу, что приведёт снижению производительности.



Сжатие HTTP-заголовков





Современная веб-страница состоит из множества элементов: изображения, JS, CSS и другие. В запросе на загрузку каждого из этих элементов браузер передаёт HTTP-заголовок. Отправляя запрошенные элементы, сервер также добавляет к ним заголовок. Всё это сопряжено с излишним расходованием ресурсов.



В HTTP/2 заголовки передаются в сжатом виде. Благодаря этому уменьшается количество информации, которой обмениваются между собой сервер и браузер. Вместо алгоритмов gzip/deflate используется HPACK. Это снижает уязвимость к атакам типа BREACH.



HTTP/2 и безопасность





Одним из важнейших требований протокола SPDY является обязательное шифрование (HTTPS) соединения между клиентов и сервером. В HTTP/2 оно обязательного характера не имеет. Однако разработчики браузеров приняли решение внедрить новый протокол только для TLS(HTTPS)-соединений. Поэтому тем, кто задумывается о переходе на HTTP/2, нужно сначала перейти на HTTPS.



Это нужно не только для HTTP/2. В поиске Google использование безопасного соединения является одним из критериев ранжирования. Многие браузеры уже помечают сайты, не поддерживающие https, как «небезопасные». Добавим также, что многие возможности HTML5 - например, геолокация - без безопасного соединения будут недоступны.



Базовая настройка HTTP/2 в Nginx и Apache





Приведём краткие инструкции по включению и базовой настройке HTTP/2 в Nginx и Apache. Как уже было сказано выше, большинство современных браузеров работают с HTTP/2 только через TLS, поэтому в конфигурации вашего веб-сервера должны быть прописаны соответствующие настройки.



Nginx





Поддержка HTTP/2 реализована только в новейших версиях Nginx (1.9.5 и выше). Если у вас установлена другая версия, вам потребуется обновить её.



После этого откройте конфигурационный файл /etc/nginx/nginx.conf и найдите в секции server следующую строку:




listen 443 ssl;




и замените её на:




listen 443 ssl http2;




Сохраните внесённые изменения и перезагрузите Nginx:




$ sudo service nginx reload




Apache





В Apache HTTP/2 поддерживается только в версиях 2.4.15 и выше. Если у вас установлена более ранняя версия, выполните обновление. После этого добавьте в конфигурационный файл следующие строки:




# for a https server
Protocols h2 http/1.1

# for a http server
Protocols h2c http/1.1




После этого перезапустите Apache. Вот и всё — для базовой настройки этого вполне достаточно.



HTTP/2 и оптимизация сайтов





HTTP/2 обратно совместим с HTTP/1.1. Поэтому вы в принципе можете не предпринимать никаких действий: работе вашего сервиса ничего не угрожает.

Но по мере перехода популярных веб-серверов и веб-браузеров на HTTP/2 вы увидите, что ваш сайт, который когда-то был оптимизирован для увеличения скорости загрузки страниц и повышения производительности, уже работает не так быстро, как раньше.



Многие способы оптимизации, успешно используемые в HTTP/1.1, в HTTP/2 работать не будут. Некоторые из них потребуется модифицировать, а от некоторых - отказаться вообще. Рассмотрим этот вопрос более подробно.



Объединение изображений в спрайты





В HTTP/1.1 было удобнее загрузить одно большое изображение, чем делать множество запросов и загружать много маленьких. Это обусловлено тем, что запросы ставятся в очередь друг за другом. Самый распространённый способ увеличения скорости загрузки заключался в объединении множественных небольших изображений в спрайт-файл.



Спрайт возвращался в ответ на единственный запрос. Даже если пользователь заходил на страницу, на которой находится всего одно небольшое изображение, нужно было загрузить весь спрайт.



В HTTP/2 c его мультиплексированием таких проблем нет, однако использование спрайтов в определённых ситуациях может оказаться полезным. Объединение нескольких изображений в спрайт (особенно если все эти изображения находятся на одной странице) помогает улучшить сжатие и таким образом снизить общий объём загружаемых данных.



Встраивание изображений с помощью DataURI





Ещё один популярный способ решения проблемы множественных HTTP-запросов в HTTP/1.1 - встраивание изображений с использованием Data URI. Это существенно увеличивает в размере таблицу стилей.



Если одновременно со встраиванием изображений для оптимизации используется ещё и конкатенация JS и CSS, пользователю скорее всего придётся загрузить весь соответствующий код, даже если он не будет посещать страницу с этими изображениями.

В HTTP/2 такая практика скорее ухудшит, а не улучшит производительность.



Конкатенация JS и CSS





Для оптимизации работы сайтов часто используется конкатенация небольших CSS- и JS-файлов. Много маленьких файлов объединяются в один большой. Таким образом удаётся обойти лимит на количество HTTP-запросов.



Однако при использовании конкатенации может возникнуть та же проблема, что и со спрайтами: зайдя на какую-то одну страницу сайта, пользователь загрузит все используемые на нём СSS- и JS-файлы (при этом очень вероятно, что большинство из этих файлов ему никогда не понадобятся). Конечно, можно тщательно отбирать файлы для каждой страницы сайта, но это будет занимать слишком много времени.



Ещё одна сложность заключается в том, что все элементы конкатенированного файла нужно вычищать из кэша одновременно. Невозможно сделать так, чтобы для одних элементов была выставлена одна дата истечения срока действия, а для других (которые к тому же и и используются гораздо чаще) — другая. Если изменить хотя бы одну строку в CSS — срок действия истечёт сразу у всех элементов.



Стоит ли пользоваться конкатенацией в HTTP/2? Если HTTP-запросы не требуют существенных затрат ресурсов, то без неё вполне можно обойтись. Загрузка множества небольших файлов стилей никакой проблемы не составит. Не будет и трудностей с истечением сроков действия и кэшированием.



Доменное шардирование





В HTTP/1.1 имеется ограничение на количество открытых соединений, Чтобы обойти это ограничение, приходится загружать статические ресурсы с нескольких поддоменов одного домена. Такой приём называется доменным шардированием; он часто используется, например, для страниц с большим количеством изображений. Это помогает увеличить скорость загрузки, но вместе с тем и создаёт дополнительные проблемы.



С переходом HTTP/2 необходимость в доменном шардировании отпадает. Вы можете запросить столько ресурсов, сколько вам требуется. Более того, в случае с HTTP/2 шардирование не улучшит производительность, а приведёт скорее к противоположному эффекту, так как создаст дополнительные TCP-соединения и будет мешать приоритизации.



Когда переходить?





Когда планировать переход на HTTP/2? Однозначного ответа на этот вопрос нет и быть не может. Дадим, однако, одну подсказку: регулярно просматривайте логи посещаемости вашего сервиса. Когда вы увидите, что большая часть посетителей используют поддерживающие HTTP/2 браузеры — можно переходить. На текущий момент поддержка HTTP/2 реализована в Chrome (в том числе и в мобильной версии для Android), Firefox, Opera, Edge, Safari.



При планировании перехода следует учитывать и особенности вашего проекта. Если у вас много пользователей, которые приходят к вам с мобильных устройств, то это означает, что вам желательно перейти на HTTP/2 как можно скорее. На смартфонах и планшетах преимущества нового протокола будут особенно очевидными. Однако и здесь нужно учитывать множество нюансов: например, во многих регионах мира до сих пор много пользователей браузера Opera Mini, а он HTTP/2 пока что не поддерживает.



Если вы планируете запускать новый веб-сервис — задумайтесь о перспективе перехода на HTTP/2. Конечно, вам ещё придётся использовать HTTP/1.1 в течение какого-то времени, но уже сейчас вы можете принять меры по оптимизации, которые облегчат вам жизнь в будущем.



Полезные ссылки





В заключение приведём для заинтересованных читателей несколько полезных ссылок по теме:







Читателей, которые по тем или иным причинам не могут оставлять комментарии здесь, приглашаем в наш блог.



Original source: habrahabr.ru (comments, light).

https://habrahabr.ru/post/278167/

Метки:   Комментарии (0)КомментироватьВ цитатник или сообщество
Александр_Рубцов

Как сделать из socks-прокси http-прокси используя Privoxy?

Понедельник, 23 Февраля 2016 г. 01:04 (ссылка)

Это цитата сообщения Rost Оригинальное сообщение

Как сделать из socks-прокси http-прокси используя Privoxy?

Ранее в блоге уже писал про это в сообщении "Как сделать из socks-прокси http-прокси используя Polipo?. Сегодня расскажу, как сделать то же самое, но с помощью программы "Privoxy".

Вам это точно не нужно!
Метки:   Комментарии (0)КомментироватьВ цитатник или сообщество
Rost

Как сделать из socks-прокси http-прокси используя Privoxy?

Пятница, 19 Февраля 2016 г. 13:26 (ссылка)

Ранее в блоге уже писал про это в сообщении "Как сделать из socks-прокси http-прокси используя Polipo?. Сегодня расскажу, как сделать то же самое, но с помощью программы "Privoxy".

Вам это точно не нужно!
Метки:   Комментарии (6)КомментироватьВ цитатник или сообщество
rss_rss_hh_new

Минимальный HTTP API Endpoint используя Elixir

Среда, 20 Января 2016 г. 14:51 (ссылка)


Давайте рассмотрим создание минимального HTTP API Endpoint используя Elixir. Так же, как и Rack в Ruby, Elixir идет в комплекте с Plug. Это универсальный инструмент для работы с HTTP соединениями.



Читать дальше →

http://habrahabr.ru/post/275563/

Комментарии (0)КомментироватьВ цитатник или сообщество
rss_rss_hh_new

[Перевод] Почему до сих пор повсеместно не используется HTTPS?

Вторник, 19 Января 2016 г. 22:56 (ссылка)


Шифрование. Мы все его любим и хотим использовать везде. Но почему оно до сих пор не применяется повсеместно?



Проблема в сертификатах?



Первый и наиболее распространённый барьер к переходу на HTTPS это цена получения, настройки и поддержки валидного сертификата. Вы должны найти поставщика сертификатов, подтвердить свою личность, заплатить за него и настроить сервер, а также своевременно продлевать.



Большинство предложений перехода на повсеместное шифрование звучат примерно так: «NSA записывает весь наш трафик, почему бы не шифровать его?». Целью подобных предложений является повышение стоимости пассивного слежения за всем трафиком, а не более сложные и целевые атаки, которые применяются злоумышленниками.



Ребята из Let's Encrypt уже догадались, что проблема с сертификатами почти полностью поддаётся автоматизации, и что её реализация для выпуска, установки, конфигурации и продления на нескольких наиболее распространённых платформах может покрыть подавляющее большинство Интернета. Замечательная работа, и, хоть и осталось сделать многое, я думаю, что мы можем считать проблему сертификатов решённой.

Читать дальше →

http://habrahabr.ru/post/275539/

Метки:   Комментарии (0)КомментироватьВ цитатник или сообщество
rss_rss_hh_new

[Перевод] Что такое RESTful на самом деле

Пятница, 08 Января 2016 г. 11:29 (ссылка)


А ваше приложение — RESTful? Чтобы ответить на этот вопрос нужно сначала разобраться что такое RESTful. Бытует мнение, что отдавать правильные коды ответов в HTTP — это уже RESTful. Или делать правильные идемпотентные HTTP-запросы — это вообще очень RESTful. Мы в Хекслете сделали практический курс по протоколу HTTP (отличия версий, отправка форм, аутентификация, куки и пр.), и в нем мы стараемся рассказать о правильном использовании запросов, но нужно понимать, что RESTful это не про HTTP, это вообще не про протоколы интернета. Современный веб и взаимодействие между браузером и сервером с помощью HTTP и URI могут удовлетворять принципам RESTful, а могут и не удовлетворять.



В сегодняшнем переводе — простое и понятное описание RESTful, и какой должна быть система, чтобы ее можно было так называть.



Читать дальше →

http://habrahabr.ru/post/274675/

Метки:   Комментарии (0)КомментироватьВ цитатник или сообщество
Aleks24

25 лет исполнилось первому интернет – сайту в мире

Четверг, 24 Декабря 2015 г. 19:40 (ссылка)
production-site.ru/novosti/...ytu-v-mire

Разработан проект в Европейском центре ядерных исследований ученым Тим Бернерс - Ли. Проект стал началом зарождения существующего в наши дни интернета
Метки:   Комментарии (0)КомментироватьВ цитатник или сообщество

Следующие 30  »

<http - Самое интересное в блогах

Страницы: [1] 2 3 ..
.. 10

LiveInternet.Ru Ссылки: на главную|почта|знакомства|одноклассники|фото|открытки|тесты|чат
О проекте: помощь|контакты|разместить рекламу|версия для pda