nuclight: (Default)
[personal profile] nuclight
Получил я на днях вот такую критику своей статьи "Netgraph для пользователя", в IRC (разговор сокращен):

<A_Z> Следует помнить, что в этом формате как узлы, так и хуки netgraph являются узлами изображенного графа — просто узлы netgraph изображены как прямоугольники (подписаны имя, ID, тип), а хуки netgraph — как восьмиугольники, и ребра, соединяющие узел со своими хуками, более жирные. Так сделано для большей наглядности и выделенности хуков, а также потому, что при обычном рисовании графа не получилось бы у одного ребра написать два названия (ведь ребро netgraph состоит
<A_Z> если кто-то прочитает и переварит это с первого раза, тот герой.
<A_Z> если помнить, что масло на котором мы жарим картошку является подсолнечным маслом, то можно предположить, что картошка является жареной и это потому, что мы жарили картошку
<levsha> ну может ведь и салом оказаться!
<Miha> картошка может оказаться салом!
<A_Z> Если название вызвало у Вас ассоциации из наркоманской фени. Вы правильно подумали. Netgraph действительно представляет собой краб^Wгриб
<nuclight> A_Z: конструктивные предложения есть?
<A_Z> nuclight: рассказывать? я уже говорил а) стиль изложения a-la петросян б) сложное построение предложений в) множесто неудачных аналогий и варваризма г) есть сомнения, что это для пользователей
<nuclight> A_Z: конструктивная критика направлена на то, чтобы исправить/улучшить, для чего необходимо указывать на конкретные вещи, и способы их исправления. Из чего следует, что 2 строчки никак не могут быть конструктивной критикой — ты к каждому пункту не привел даже пяток примеров, из которых можно было бы проследить тенденцию твоих субъективных впечатлений.
<nuclight> A_Z: стиль изложения — в каком месте? почему не давно изветсный прием отдыха читателя среди горы информации, напрмер? Сложное построение предложений — где? примеры, как было бы построить лучше (я вообще-то следил и слишком сложные предложения не делал)? Множество неудачных и варваризма — какие именно? в чем их неудачность и варваризм для тебя? какие были бы лучше? Есть сомнения — в чем это выражается? где следовало разжевать еще?
<nuclight> A_Z: уже сам факт того, что я тебе должен встречные вопросы задавать говорит, что это не была конструктивная критика. Литературные критики во времена оные целые эссе писали, тебе же нужно было написать от силы килобайта два, а не сорок два, как мне.
<A_Z> nuclight: вот тебе мои два килобайта


И вот текст собственно рецензии (кладу тут для истории, чтоб не потерялся):
Рецензия без запятых.

После прочтения статьи Вадима Гончарова "Netgraph для пользователя" я окунулся
в мир грибов и дисктретной математики. В своем труде Вадим рассказывает нам об
удивительном мире "Netgraph" мистической сетевой подсистеме чьи возможности не 
имеют границ и лимитированы лишь возможностью пользователя. Для расширения
этого лимита Вадим как Карлос Кастанеда рекомендует нам _правильный путь_. 

Дойдя наконец до первого осмысленного упоминания этой системы читатель
встретится с лирическими отступлениями, пояснениями и аналогиями которые по
мнения Вадима не всегда удачны а некоторые даже плохи. Радостью для читателя
будет то что процедурные системы это как пульт от телевизора а проективные
совсем не уперлись и читать про них не нужно ведь netgraph процедурный. Правило
80/20 вовремя проводит черту и дает четко понять что 80 процентов повествования
bullshit (дэрьмо, булщит) а 20 и есть та информация необходимая для понимания
но к слову сказать мы с вами узнаем как принципы именования графьев. <unnamed>,
mpd805-stkp и мы стремительно ворвемся в интерлюдию (тех кто не умеет читать а
любит иллюстрации)..хмхм..прямоугольники, восьмиугольники и трапэции 
(белые на белом) плавно переходят в ООП. 

В главе про объекто-ориентированный и финкциональный автор четко выделил для
уставшего и сбитого с толка читателя ключевые (keyword, киводз) слова
инкапсуляции, полиморфизм, сообщений и generic. Все остальное попадает под
правило 80/20.

На протяжении всей статьи Вадим как и персонаж рассказа Письмена Бога (Борхес) 
который является ацтекским служителем культа по имени Тсинакан ищет способ 
которым Бог мог бы передать свои письмена всемогущества тому кто способен их прочесть.
В процессе расшифровки Вадим понимает смысл бытия и секреты устройства вселеной.
Однако слова всемогущества так и остаются тайной для читателя: Вадим
отказывается произносить их. "Кто видел эту вселенную кто постиг пламенные
помыслы вселенной не станет думать о человеке о жалких его радостях и горестях
даже если он и есть тот самый человек. вернее сказать. был им" объясняет он. 
В заключении Вадим приводит несколько расшифрованых писем но сразу уточняет что
для загадочного продактсион (production) они не годятся. Если бы Борхес начинал
писать сейчас то прекрастный рассказ "Маны Netgraph" и Вадима в соавторстве с 
Карлосом Кастанедой..Это как цветение сакуры я вас уверяю.
----
я бы хотел чтобы:
1. Автор определил до момента написания статьи какие вопросы интересуют читателей
и какой уровень их познания требуется и писал исходя из этого. 
2. Автор составил план статьи или цикла статей, дабы четко прослеживалась логика 
поэтапного наращивания материала без возможности перечитать томик квантовой физики
в процессе объяснения почему бутерброд падает.

Получилось смешно, да, но более-менее вразумительного перечня недостатков статьи я так и не получил. Как сказал drook, «ну вообще кто бы там не написал тебе ответ который на фбаше цитируется, он является примером еще более сложной статьи, по сложности чтения это где-то на уровне "Так сказал Заратустра"»). Путем опроса выяснилось, что в основном претензии идут к аналогиям, которые непонятны, и к излишней сложности в некоторых местах:

<drook> я про проективное и процедурное и про телевизор думал минут 5, потом решил читать дальше
<drook> если бы я знал что такое проективное и процедурное то наверное мне было бы понятно про пульт, но я не знаю и мне непонятно
<drook> телевизор включается/выключается/переключает каналы и показывает картинку которая сама по себе содержит образы. и, потом, ты видел современные пульты телевизооров ? там под 80 кнопок


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

Лирическое отступление и пояснения на аналогиях


Представьте себе, что Вы — гриб IP-пакет и, одновременно, — радиоволна пассажир, прибывший в default city железной дорогой. Город — это роутер, вокзалы — интерфейсы. Прибывшие пакеты-пассажиры обрабатываются и перемещаются к своим вокзалам (или остаются в городе) системой метро. На станциях может поменяться не только маршрут пакета (какая станция дальше), но и что-нибудь еще — тут газету купил, там милиция подержала в очереди шейпера...
Вот, в каком-то приближении, метро и будет как netgraph — станции как узлы, перегоны между ними как ребра. Не каждый пакет обязан пойти в netgraph — многие будут обработаны традиционным способом (поехал на автобусе).

Но это плохая аналогия.

Для другой сначала сделаем лирическое отступление с кратким пересказом содержания http://www.intuit.ru/department/os/osunix/ (первые 3 лекции), где рассказывается, что человеко-машинные системы бывают проективные и процедурные.

Процедурные cистемы предоставляют (ограниченный) набор функций (процедур) внутри прикладной области: например, кнопки пульта управления телевизором или пункты меню, типа "недавно открывавшиеся документы". Достоинства: новичок может работать с системой почти сразу, быстрота решения предусмотренной разработчиком ситуации.

Проективные cистемы — это когда на языке инструментальной области составляется проект, описывающий ее предполагаемое поведение, затем машина его выполняет. Примером служит Unix way — задача "посмотреть самый свежий из отчетов" решается так: ls -dt1 `grep -il отчет *` | head -1
Здесь высокий входной порог: сначала требуется изучить большое количество документации. Предполагает профессионализм и ответственность (от rm -rf ~/* не оградят).

Так вот, netgraph — система проективная, и позволяет делать с сетевыми пакетами примерно то же, что pipeline'ы в Unix — с текстовыми данными. Много мелких модулей-программ, каждый делает свою узко очерченную часть работы, и средства их комбинирования. Вставили звено в цепочку — раз — и уже появилась компрессия данных (без изменения соседних модулей).

До netgraph в сетевую подсистему новые фичи добавлялись по принципу "для этой задачи мы сделаем штуку, для чего поправим сотню мест". Нужен бридж — пошли в L2 вклинимся, будет специальная обработка для случая бриджа. Нужен транк — сделаем псевдоинтерфейс, которому тоже свою обработку в общей части стека напишем. Завтра что-то новое будет — в коде несчастных ether_*() появятся очередные if () {...}. А в случае netgraph общий код выделяется в ng_ether один раз, и больше его править не нужно, потом просто цепляются ng_bridge, ng_one2many и т.д.

Известно правило 80/20, в разных формулировках, применимое во многих областях (не всегда в именно такой буквальной пропорции, конечно). И если 80% задач — типовые и решаются сравнительно легко, то netgraph предназначен для решения тех 20% задач, которые сложные, и на которые нужно потратить, соответственно, больше усилий.

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

Но у ЖЖ довольно жесткие ограничения на объем поста — 65536 символов в UTF-8, в котором русские буквы занимают 2 байта, а латиница 1. Довольно скверное ограничение, что лимит стоит именно в UTF-8 — не знаешь, сколько же у тебя точно будет места. Статья получилась примерно в 42 тысячи знаков, и, чтобы влезло, этот раздел первым пошел под сокращение. Вот так он выглядел в черновике статьи:

Лирическое отступление и пояснения на аналогиях


Представьте себе, что Вы — гриб IP-пакет и, одновременно, — радиоволна пассажир, прибывший в default city железной дорогой. Город — это роутер, вокзалы — интерфейсы. Прибывшие пакеты-пассажиры обрабатываются и перемещаются к своим вокзалам (или остаются в городе) системой метро. На станциях может поменяться не только маршрут пакета (какая станция дальше), но и что-нибудь еще — тут газету купил, там милиция подержала в очереди шейпера...
Вот, в каком-то приближении, метро и будет как Netgraph — станции как узлы, перегоны между ними как ребра. Не каждый пакет обязан пойти в Netgraph — многие будут обработаны традиционным способом (поехал на автобусе).

Но это плохая аналогия.

Для другой сначала сделаем лирическое отступление с кратким пересказом содержания http://www.intuit.ru/department/os/osunix/ (первые 3 лекции), где рассказывается, что человеко-машинные системы бывают проективные и процедурные.


Процедурные cистемыПроективные cистемы
Набор функций (процедур) внутри прикладной области, описываемых в терминах прикладной области. Набор решений ограничен.
Здесь пользователю не нужно долго изучать систему (более того, часто от внутренностей его тщательно оберегают), навыки достаточно простые. Система сводится к набору предписаний вида "нажми то, получишь это" или даже вообще "командует" пользователем, проводя его по шагам. Достоинства: новичок может работать с системой почти сразу, быстрота решения предусмотренной разработчиком ситуации.
На языке инструментальной области составляется проект, описывающий ее предполагаемое поведение, затем машина его выполняет.
Задачи решать сложно, высокий входной порог: сначала требуется изучить большое количество документации. Предполагает профессионализм и ответственность (что понимает, что делает, от rm -rf ~/* не оградят).
Примеры:
  • Пульт управления телевизором

  • Мастер настройки Internet в Windows (проводит по шагам)

  • Пункт меню "недавно открывавшиеся документы"

Пример:
Unix way — посмотреть в документах самый свежий из отчетов:
ls -dt1 `grep -il отчет *` | head -1

Так вот, Netgraph — система проективная, и позволяет делать с сетевыми пакетами примерно то же, что pipeline'ы в Unix — с текстовыми данными. Много мелких модулей-программ, каждый делает свою узко очерченную часть работы, и средства их комбинирования. Вставили звено в цепочку — раз — и уже появилась компрессия данных (при том, что соседние модули об этом не в курсе, их переконфигурировать не надо).

До Netgraph в сетевую подсистему новые фичи добавлялись по принципу "для этой задачи мы сделаем штуку, для чего поправим сотню мест". Нужен бридж — пошли в L2 вклинимся, будет специальная обработка для случая бриджа. Нужен транк — сделаем псевдоинтерфейс, которому тоже свою обработку в общей части стека напишем (причем не для каждого типа интерфейса еще, кстати). Завтра что-то новое будет — в коде несчастных ether_*() появятся очередные if () {...}. А в случае Netgraph общий код выделяется один раз, и больше его править не нужно, потом просто цепляются ng_bridge, ng_one2many и т.д.

Известно правило 80/20, в разных формулировках, применимое во многих областях (не всегда в именно такой буквальной пропорции, конечно). И если 80% задач — типовые и решаются сравнительно легко, то Netgraph предназначен для решения тех 20% задач, которые сложные, и на которые нужно потратить, соответственно, больше усилий. Но и людей, которые с ними сталкиваются и решают, соответственно, не так много, а чем специалистов меньше, тем они ценнее. Такие люди не удовлетворяются 20% информации, а копают как можно глубже. Какой процент читателей перешел по ссылкам выше, к какой категории они относятся?.. :) То-то же.

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

Исходной задумкой было ответить на задаваемый на форумах многими, не понимающими netgraph, вопрос: зачем он нужен, если существуют счетчики netflow, демоны туннелей, и много других готовых вещей под задачи? Спрашивают, понятно, обычно пользователи других ОС, не понимающие, зачем такая фича нужна. Если отвечать на него кратко, то это разница в подходах Windows и Unix — в первом принято на каждый чих искать программу (потому что в базовой системе средств мало), а также есть тенденция программ тяготеть к комбайнам — запихнуть как можно больше функций в одно приложение. Но такой ответ вызовет встречные вопросы, ведь мы, вроде бы, уже на *nix-системе, да и программы, типа того же vtun, вовсе не комбайны...

Причина в том, что люди мало задумываются о том, как они делают те или иные вещи, в чем разница в организации, да часто и вообще не любят думать. Оригинал на http://www.intuit.ru/department/os/osunix/ дает развернутый ответ аж в трех лекциях, причем каждая еще и на нескольких html-страницах. А те, кто не любит думать, не любит и много читать, обычно отмазываясь нехваткой времени. Почему отмазка? А вот я сейчас, в том числе и поэтому, начну сокращенно пересказывать разницу, приводя цитаты. В первой же видим аккурат про "нехватку времени":
Рассмотрим самый, на наш взгляд, естественный алгоритм решения любой задачи:
1. уяснить задачу;
2. выбрать самый подходящий инструмент решения (самый подходящий, а не самый знакомый!);
3. освоить этот инструмент (начиная с изучения документации).
4. придумать по возможности красивое решение;
5. зафиксировать это решение (чтобы можно было в случае чего повторить);
6. применить его.

Казалось бы, спорить не с чем, но как часто мы поступаем строго наоборот!

Желая "сэкономить время", мы нередко начинаем с того, что так и эдак применяем попавшиеся под руку инструменты (6) и даже начинаем набрасывать кое-какие сценарии или проекты решения (5). Потом мы задумываемся над тем, как же решить нашу задачу "по уму" (4), и понимаем, что инструмент нам, в сущности, незнаком, что надо изучать руководство (3). Из руководства выясняется, что инструмент нам не подходит, и приходится искать другой (2). И только тогда мы понимаем, что для этого надо разобраться, какую именно задачу мы решаем (1).

Тут не могу не поплеваться ядом в сторону большинства нынешних "инженеров" и "админов", которые очень часто поступают как раз так: схватили первый попавшийся howto и начали бездумно применять. А уж как часто это можно наблюдать в среде быдлокодеров на PHP... впрочем, я отвлекся.

Итак, есть две области человеческой деятельности. Одна — прикладная — связана с постановкой и решением задач определенного класса. Другая — инструментальная — связана с разработкой средств для решения прикладных задач.. Пользователь, например типограф, мыслит в терминах своей прикладной области: гарнитура, кегль, абзац... Машина же — универсальный инструмент, и чтобы она могла решать задачи пользователя в прикладной области, сначала нужен специалист в инструментальной — создать инструмент под задачу. Но далее этот специалист не нужен, пользователь остается один на один с машиной и инструментом. Какие возможны подходы?
Первый, наиболее очевидный путь "сближения" человека и машины — вернуть машине-орудию ее былую простоту. Несмотря на сложность системы и разнообразие решаемых ею задач, вполне возможно оставить для взаимодействия с человеком только те управляющие возможности, что лежат в прикладной области. Иными словами, человеку будет доступно (и известно) лишь то, что относится к постановке и решению задачи. При этом инструментальную область — все, что относится к устройству системы и управляет ходом решения, — следует оставить доступной только разработчикам и экспертам, а от конечного пользователя скрыть.

Кем себя будет ощущать пользователь такой системы? Заказчиком и одновременно потребителем, то есть клиентом: он описывает на доступном ему языке продукт, который хочет получить, и отдает это описание на отработку машине. Когда работа машины окончена, то, что получилось, немедленно идет в дело. Предполагается, что некоторые параметры продукта (а иногда и все) машина будет узнавать уже по ходу работы, задавая наводящие вопросы, опять-таки на доступном клиенту языке. Другой вариант — держать перед глазами клиента некую модель требуемого объекта, которая изменялась бы всякий раз, когда изменяется сам объект. Это называется WYSIWYG, What You See Is What You Get ("что видишь, то и получишь"). В этом случае можно не вводить вообще никакого промежуточного языка, оставив клиенту только те действия, смысл которых понятен из изменений модели.

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

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

Администратор человеко-машинной системы и "системный администратор" не одно и то же. Это может быть программист, оператор СУБД или, скажем, автолюбитель, который разбирает и собирает свою автомашину с закрытыми глазами. Главное, что он способен управлять системой, потому что знает, как она работает. Нередко и заказчик системного продукта, и потребитель — некто другой, не включенный в систему; иногда (часто в случаях реального системного администрирования) четко выраженного заказа вообще нет: начальник хочет, чтобы "все работало как следует". Администратор здесь — производитель системного продукта, иными словами — тот, кто выполняет (часто для других) работу при помощи машины.

Такой подход требует, чтобы в системе были предусмотрены разнообразные универсальные и специализированные средства создания решений любых возможных задач. Для компьютера это высокоуровневые языки программирования и отдельные программы для элементарных взаимодействий с системой. Для автомобиля — набор удобных ключей и прочих инструментов для работы с любой деталью и всевозможные насосы-домкраты. Конечно, необходимо, чтобы и пользователь свободно владел этими средствами. Решив (чаще всего чисто умозрительно) поставленную задачу, администратор дает команду машине: "Делай по моему проекту" (или ударяет в нужное место кувалдой). Машина работает, а пользователь занимается другими делами, не забывая, однако, приглядывать за системой: хорошо ли справляется с задачей его творение, не стоит ли где подправить? Составление проекта, по которому машина будет решать задачи самостоятельно, — ключевая особенность, иначе пользователю пришлось бы делать часть формализуемой работы за машину, поэтому организованные таким образом системы можно назвать проективными.

А вот хорошо описано, почему howto не заменяют документацию:
Самый простой способ взаимодействия с проективной системой — метод проб и ошибок; это просто вырожденный вариант тестирования и отладки. Специфика этого метода применительно к проективной системе в том, что без знания устройства системы, без общего понимания того, как она начнет вести себя на основании сделанного проекта, на сто проб скорее всего придется сто ошибок, и эффективность метода будет нулевой. Поэтому главная часть проективной системы — полная и грамотная документация. Нет документации — нет системы. Вдумчивое чтение документации может свести количество проб к одной, а количество ошибок — к нулю (звучит невероятно, однако, если пользователь достаточно опытен, часто получается именно так).

Еще один простой способ взаимодействия с системой — создание проекта по примерам. Допустим, нам надо запустить почтовый сервер (сервер — это программа, а не компьютер!), да не просто так, а чтобы он принимал электронную почту только с определенных компьютеров сети. Выбираем для этого из примеров настроек (то есть проектов) почтового сервера тот, в котором заявлена "фильтрация почты". Дальше идет цикл тестирования-отладки. Запускаем сервер. Работает! В самом деле, откуда-то принимает почту, а откуда-то — нет. Заглядываем в проект. Там — порядка дюжины каких-то секций: одна отвечает за способ доставки почты, другая — за то, где и как ее хранить и т. д., все это мы узнаем, бегло глянув в документацию. Находим секцию, отвечающую за фильтрацию почты. Читаем соответствующий раздел документации повнимательнее. Оказывается, существует черный список отправителей и черный список компьютеров. Изменяем, перезапускаем сервер. Нет, нам нужен не черный, а белый список (перечень тех, от кого следует принимать почту). Читаем документацию еще внимательнее. Там есть и белый список, но в примере его нет. Исправляем настроечный файл сообразно документации, а черные списки удаляем и снова перезапускаем сервер. Если в остальном мы были внимательны, теперь он работает как надо.

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

За принципами построения проективных систем — минимизация затрат, умопостижимость контекста, информационная открытость, персональная ответственность (и следствиями из них) — отсылаю к http://www.intuit.ru/department/os/osunix/2/2.html (там еще написано, почему совместно совершенствовать мотоцикл лучше парка велосипедов). Сейчас же пора перейти к процедурным системам — к тому самому пресловутому телевизору.
Процедура как суррогат поступка

Процедурной мы будем называть человеко-машинную систему, доступную человеку в виде набора функций (процедур) внутри прикладной области, описываемых в терминах прикладной области и приводящих к наглядному или гарантированному изменению свойств объекта. Например, человеко-телевизор — полностью процедурная система: все задачи, которые ставит перед ней человек, описываются в терминах "программа", "громкость", "контраст" и т. п. Телевизор же (вернее, инструкция к нему) общается с пользователем на том же языке (кажется, в нем есть только один новый термин — "кнопка", все остальные, включая названия кнопок, повторяют известное пользователю).

Система в самом общем виде работает так: человек описывает, какой продукт он хочет получить, а машина рассказывает, какие действия надо для этого предпринять. Естественно, возможны варианты: часто человек не в состоянии вспомнить все свойства продукта, и машине приходится потихоньку выспрашивать их; так, например, устроен, "мастер подключения к Internet" в Windows 98 и прочие подобные ему "мастера" (wizards). Почти всегда стадия "какие действия предпринимать" этими мастерами и ограничивается: после того, как свойства продукта описаны, задачу уже можно решить, не посвящая пользователя в тонкости решения. Наконец (отличительная особенность процедурных систем!), под типовую пользовательскую задачу, скорее всего, найдется готовый вариант решения, так что пользователю останется только нажать кнопку, скажем, "форматировать текст" и наслаждаться результатом.

Поскольку система на самом деле гораздо сложнее, то для пользователя создается легенда — описание рычагов управления системой так, как если бы она только из них и состояла.
Недостаток легенды в том, что придерживаться ее всегда и во всем невозможно. Одни и те же — по легенде — объекты начинают вести себя в разных ситуациях по-разному, потому что соответствуют различным типам объектов системы. Типичный пример легенды — понятие иконки (значка, icon) в Windows. Иконки в обозревателе ведут себя не так, как некоторые иконки на рабочем столе, и совсем не так, как иконки в панели управления.

Пользователь процедурной системы зачастую не знает, как именно он добился от нее желаемого результата и далеко не всегда может с первого раза воспроизвести свои действия. Нажимал-нажимал на кнопки — и вышло. Как? А кто ж ее знает. Здесь работает накопленный опыт общения с системой, возможно, даже некое представление об ее истинном устройстве, добытое из системы в обход предусмотренных каналов информации и оттого не поддающееся формализации. Явление это имеет название black magic (черная магия) или voodoo.

Принципы построения процедурной системы:

  • Принцип ограниченной осведомленности — устройство системы скрыто, документации мало. Чтоб и голову не забивал, и систему не попортил.

  • Принцип гарантированных навыков — пользователь не обязан что-то особенное уметь для того, чтобы начать работать с процедурной системой, а если чему-то для этого все-таки надо учиться, то научиться надо как можно быстрее. «Нельзя основной упор делать на команды, требующие от пользователя решения мыслительной задачи одним сложным действием, лучше пускай задача решается механическим повторением ряда простых действий. С этим же связано обязательное присутствие в таких системах процедур Undo и Redo (причем чаще всего — многоуровневых), потому что механическая ошибка (и даже повторная!) — дело вполне обычное.»

  • Принцип перекрытия процедур — средства интеграции процедур между собой слабы, поэтому создается как можно больше процедур, последовательным применением ряда которых можно добиться нужного результата. В итоге, во-первых, процедур (кнопочек, рычагов, пунктов меню) в системе становится очень много. «Во-вторых, многие задачи так и приходится решать: путем последовательного применения нескольких других решений, используя при этом только часть их свойств (например, создать табличку, после чего вручную изменить толщину рамочек вокруг отдельных полей — это в случае, если ни один из готовых стилей таблиц не подходит). В самом деле, проще убедить пользователя в том, что готовое решение его устроит, чем подыскивать действительно удовлетворяющее его решение.»

  • Принцип делегирования ответственности — поскольку пользователь не разбирается в системе, гарантию качества может давать только разработчик. «Типичный признак процедурной системы — обилие запросов на подтверждение выбранного действия. Иногда подтверждения бывают двойные: за первым "Вы уверены?" следует "Вы действительно уверены?". Ответственный за систему — разработчик — обязан таким способом отмечать точки управления системой, в которых он перекладывает ответственность на пользователя.»

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

Сводную табличку характеристик проективных и процедурных систем можно посмотреть на http://www.intuit.ru/department/os/osunix/3/3.html — мне же осталось вернуться к netgraph. Что лучше, проективная или процедурная система? А ни то, ни другое. Лучше и то, и другое сразу. Хорошая система должна предоставлять как удобство для новичка (простые вещи — понятны и просты же), так и оставлять возможность для профессионала залезть в потроха и сделать руками то, что он хочет, а обычный интерфейс не позволяет, и при этом не мешать ему в этом — если система навязывает единый стиль действий "как для новичка", она будет мешать.

В случае netgraph имеется как минимум один положительный пример такого симбиоза — mpd. Он сам свои узлы конфигурирует, предоставляет относительно простой интерфейс в терминах более прикладной области, нежели сборки руками — но при при этом не мешает залезть в потроха, посылать узлам дополнительные сообщения, воткнуть в некоторые места свои узлы, собрать при желании вообще свой backend (set link type ng и вперед), и т.д.

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

Date: 2011-02-11 09:46 am (UTC)
From: [identity profile] cae32.livejournal.com
Пишите. На неконструктивную критику не обращайте внимания. Нормальный критик напишет свою статью, лучше, чтобы показать как...

Date: 2011-02-11 10:26 am (UTC)
From: [identity profile] morbow.livejournal.com
Чувак наверное хотел чтобы его не просто с ложечки накормили, но заливали уже разжёванную и смоченную слюной консистенцию прямо в горло. Если бы ему нужно было что-то понять, он бы не не выливал помои на автора, а воспользовался поиском и почитал бы о не понятном до просветления.

Date: 2011-02-11 06:43 pm (UTC)
From: [identity profile] kondybas.livejournal.com
Нетграф - хорошо, но нетипично. Его гораздо проще объяснить программеру с ОО бэкграундом, чем админу/сетевику без программерской/ОО базы.

Кстати, давеча топтался по особенностям реализации ipfw/ng_ipfw. Если ng_ipfw понимает куки лонг-инт, то ipfw параметром команды netgraph принимает только двухбайтовый инт, не более 65535. Очень некрасиво получилось.

Date: 2011-02-11 07:26 pm (UTC)
From: [identity profile] nuclight.livejournal.com
> Нетграф - хорошо, но нетипично. Его гораздо проще объяснить программеру с ОО бэкграундом, чем админу/сетевику без программерской/ОО базы.

Да ну, сколько там того ОО в количестве понятий? И то, из изначального, куда проще, чем современное. Сетевикам же подобный концепт должен быть знаком - много где бывает несколько разных instance одного и того же типа. Простейший пример - сетевой интерфейс, у каждого свои параметры. Да и в документации это много где даже и называют словом "объект", в бытовом, не ООП, смысле.

> Кстати, давеча топтался по особенностям реализации ipfw/ng_ipfw. Если ng_ipfw понимает куки лонг-инт, то ipfw параметром команды netgraph принимает только двухбайтовый инт, не более 65535. Очень некрасиво получилось.

А где он его понимает как лонг-то? Там исторически так было для dummynet, по диагонали пролистал, внешний код не может больше 65535 выставить, соответственно, никаких проблем сходу не вижу.

Date: 2011-02-11 08:35 pm (UTC)
From: [identity profile] kondybas.livejournal.com
ну, я могу на хук нг_ипфв повесить куку 1000000, и даже лист ее так и показывает. Но вот уже сам ипфв не понимает такого - и ругается.

Date: 2011-02-11 08:40 pm (UTC)
From: [identity profile] nuclight.livejournal.com
Что значит "повесить на хук куку"? Кто именно и как именно "ругается"? Что конкретно делается-то?

Date: 2011-02-11 08:46 pm (UTC)
From: [identity profile] kondybas.livejournal.com

+ mkpeer ipfw: nat 100000 out
+ name ipfw:100000 nat_100000
+ list
There are 3 total nodes:
Name: ipfw Type: ipfw ID: 00000001 Num hooks: 1
Name: nat_100000 Type: nat ID: 00000003 Num hooks: 1
Name: ngctl6626 Type: socket ID: 00000002 Num hooks: 0
+ info ipfw:
Name: ipfw Type: ipfw ID: 00000001 Num hooks: 1
Local hook Peer name Peer type Peer ID Peer hook
---------- --------- --------- ------- ---------
100000 nat_100000 nat 00000003 out
+
From: [identity profile] nuclight.livejournal.com
Ну это же не "кука" (ip_fw_args.cookie), а имя хука всего лишь. Ругается-то кто? /sbin/ipfw? Ну, можно рассматривать это как фичу: создать 65534 хука для выхода пакетов из ipfw в netgraph, а потом еще столько же - для их возврата :)
From: [identity profile] kondybas.livejournal.com
Номер хука - и есть кука для ipfw netgraph, так что сжульничать не получится.

В общем, не особо проблематично, просто я сдуру решил в хуках-куках накодировать приоритеты-направления для наглядности. Но вот, недокументированая такая грабля, на которую довольно неприятно наступить.
From: [identity profile] nuclight.livejournal.com
А, это из man ipfw термин. Я в исходниках не в то место посмотрел...

Вообще же лимит 65534 для ipfw настолько типичен, что было бы странно ждать чего-то иного. Впрочем, недокументированность - это плохо. Сделайте send-pr про man-страницу (а еще лучше с патчем).

Есть хак с tablearg

Date: 2011-02-18 01:36 pm (UTC)
From: [identity profile] nuclight.livejournal.com
В IRC поднимался схожий вопрос, про то, что в 8.1 убрали возможность создания пайпов с номером больше 65535, возвращает ipfw: setsockopt(IP_DUMMYNET_CONFIGURE): Invalid argument. Судя по коду, такая же возможность существует и для netgraph, причем должно работать и сейчас (структуры поменяли, оно больше не cookie называется, но 32 бита таки). То есть таки можете кодировать направления (только слишком много хуков не делайте, будет медленно).

Date: 2011-02-28 02:46 pm (UTC)
From: [identity profile] sem-lj.livejournal.com
Убери пожалуйста ссылку на мой домен. Ты все равно себе все скопипастил.

Date: 2011-02-28 03:03 pm (UTC)
From: [identity profile] ast-pm-105.livejournal.com
Приветствую вас.

Пытаюсь самостоятельно разобраться в настройке ng_nat, но что-то не получается - запутался. Интересует принцип установки режимов работы ng_nat через ngctl msg nat: setmode { flags= mask= }.

Я нашел ваш скрипт ( http://antigreen.org/vadim/freebsd/ng_nat/ng_nat.sh ).
Там есть такая функция ng_nat_set_mode(), а в ней проверка на необходимость установки какого-либо режима с последующей конфигурацией через setmode.

Если можно вопрос: как правильно устанавливать параметр setmode mask= ? У вас при начальном конфигурировании экземпляра ng_nat он установлен в mask=0. Я прочитал в мане про libalias, что оно ожидает от нас флаги и маску которая указывает какие конкретно биты надо менять (?). Я вот не программист и мне как-то сложновато сходу понять в чем соль :)

Скажем если я устанавливаю конфигурацию вида:
log=1
deny_incoming=2
same_ports=4
unregistered_only=16
reset_on_addr_change=32

это значит 32+16+4+2+1=55 (00000000 00000000 00000000 00110111)
ngctl msg nat: setmode { flags=55 mask=0 }

А если я теперь хочу на лету выключить логирование то какое значение маски применять?

Может достаточно просто указать новое значение при нулевой маске чтобы ng_nat заместил все старые биты им:
ngctl msg nat: setmode { flags=54 mask=0 }

Или надо все же указать еще и маску 4294967294 (11111111 11111111 11111111 11111110)
ngctl msg nat: setmode { flags=54 mask=4294967294 }


Заранее спасибо.
From: [identity profile] nuclight.livejournal.com
> Если можно вопрос: как правильно устанавливать параметр setmode mask= ? Я прочитал в мане про libalias, что оно ожидает от нас флаги и маску которая указывает какие конкретно биты надо менять (?). Я вот не программист и мне как-то сложновато сходу понять в чем соль :)

Маска применяется к флагам как побитовое AND (т.е. логическое И на каждый бит). В исходниках там такая строчка:
la->packetAliasMode = (flags & mask) | (la->packetAliasMode & ~mask);
(для незнающих Си: & есть AND, | есть OR, ~ есть NOT).

Как правило, это означает, что если все флаги, которые передаются туда, надо включить - то маске можно просто присвоить такое же значение как и самим flags. Если какой-нибудь флаг надо отключить - в маску пишется значение, как если бы он наоборот включался, а вот в сами флаги он не приплюсовывается (ноль).

> У вас при начальном конфигурировании экземпляра ng_nat он установлен в mask=0.

В моем скрипте ошибка, спасибо за указание. Исправил.

> А если я теперь хочу на лету выключить логирование то какое значение маски применять?

Поскольку для log=1, то:
ngctl msg nat: setmode { flags=0 mask=1 }

> Может достаточно просто указать новое значение при нулевой маске чтобы ng_nat заместил все старые биты им:
> ngctl msg nat: setmode { flags=54 mask=0 }
> Или надо все же указать еще и маску 4294967294 (11111111 11111111 11111111 11111110)

Нет, при нулевой маске он не изменит ничего. Все "старые биты заместятся новым значением" при максимальной маске, 0xffffffff.

February 2017

S M T W T F S
   1 234
567891011
12131415161718
19202122232425
262728    

Style Credit

Expand Cut Tags

No cut tags
Page generated Jun. 20th, 2025 11:23 pm
Powered by Dreamwidth Studios