Я хотел бы добавить ответ на этот вопрос, так как в последнее время я бродил по некоторой хорошей, плохой, но в основном уродливой Java, и у меня появилась новая огромная нагрузка от грубых обобщений в отношении Java и разработчиков Java против JS и Разработчики JS, которые могли бы основываться на чем-то, смутно напоминающем полезную правду.
Есть IDE, но может быть полезно понять, почему их не было много
Я пробовал Webstorm сейчас, когда я был привлечен к разработке Node, и это не так уж и плохо, что я действительно купил его, но я по-прежнему склонен открывать js-файлы в Scite чаще, чем WS. Причина этого в том, что вы можете сделать намного больше с гораздо меньшими затратами в JS, но также потому, что работа пользовательского интерфейса дает немедленную обратную связь, инструменты разработки для браузера (в частности, Chrome и Firebug) на самом деле довольно хороши, и (учитывая контексты, не связанные с браузером) ) повторное выполнение измененного кода быстро и легко без этапа компиляции.
Еще одна вещь, в которой я полностью убежден, это то, что IDE в основном создают свои собственные требования, используя небрежный код, который вы действительно не можете позволить себе в JavaScript. Хотите узнать, как мы справляемся в JS? Это может помочь начать с попытки написать что-то нетривиальное в Java без IDE и обратить пристальное внимание на то, что вы должны начать делать и думать, чтобы реально иметь возможность поддерживать / изменять этот код без перемещения IDE вперед. IMO, те же самые вещи по-прежнему важны для написания поддерживаемого кода независимо от того, есть ли у вас IDE или нет. Если бы мне пришлось написать 4-летнюю программу обучения программированию, это не позволило бы вам в первые два года касаться среды IDE, чтобы избежать искажения инструментов и зависимостей.
Состав
Опытные разработчики JS, работающие со сложными приложениями, могут и действительно структурировать свой код. На самом деле это одна вещь, которую мы склонны делать лучше с ранней историей, в которой не было IDE для чтения кода для нас, но также и потому, что мощно выразительные языки могут очень мощно выражать полностью не поддерживаемые кодовые базы аварий, если вы не будете вдумчиво кодировать.
У меня на самом деле была довольно крутая кривая обучения в понимании нашей кодовой базы Java в последнее время, пока я, наконец, не понял, что ничего из этого не было правильным ООП. Классы были не более чем набором свободно связанных методов, изменяющих глобально доступные данные, сидящие в bean-компонентах, DTO или статических геттерах / сеттерах. Это в основном тот же самый старый зверь, которого ООП должен был заменить. Поэтому я перестал искать и думать о коде в принципе. Я только что выучил сочетания клавиш и проследил путаницы, и все прошло гораздо более гладко. Так что, если вы уже не в привычке, подумайте об ООП.
Хорошо структурированное приложение JS на самом высоком уровне будет состоять из сложных функций (например, jQuery) и объектов, взаимодействующих друг с другом. Я бы сказал, что отличительной чертой хорошо структурированного, легко поддерживаемого приложения на любом языке является то, что оно легко читаемо, смотрите ли вы на него с помощью IDE или Notepad ++. Это одна из основных причин, по которым я крайне критичен к внедрению зависимостей и тестированию TDD, доведенному до крайности.
И, наконец, отпустить занятия. Изучите прототип наследования. Это на самом деле довольно элегантно легко реализовать, когда вам действительно нужно наследование. Однако я считаю, что в JS подходы к компоновке работают намного лучше, и я лично начинаю болеть и переживаю ночные кошмары EXTJS каждый раз, когда вижу более одного или двух уровней наследования на любом языке.
Основные принципы Сначала
Я говорю об основных вещах, которые должны быть извлечены из всех других хороших практик: СУХОЙ, ЯГНИ, принцип наименьшего удивления, четкое разделение проблемных областей, запись в интерфейс и написание разборчивого кода - мое личное ядро. Все, что немного сложнее, что защищает от отказа от этих практик, следует рассматривать как помощь Kool на любом языке, но особенно на таком языке, как JavaScript, где очень легко оставить наследие очень запутанного кода для следующего парня. Например, слабая связь - это отличная вещь, пока вы не зайдете так далеко, что не сможете даже определить, где происходит взаимодействие между объектами.
Не бойтесь динамического набора текста
В JavaScript не так много основных типов. По большей части, правила динамического приведения являются практичными и простыми, но стоит изучить их, чтобы вы могли лучше научиться управлять потоком данных без ненужных приведений и бессмысленных процедур проверки. Доверьтесь мне. Строгие типы отлично подходят для производительности и выявления проблем при компиляции, но они не защищают вас от чего-либо.
Изучите дерьмо из функций и замыканий JS
Первоклассные функции JS являются, пожалуй, главной причиной, по которой JS выиграл «Единственный язык, который стоит прикасаться к клиентскому веб-сайту». И да, на самом деле была конкуренция. Они также являются центральной особенностью JS. Мы строим объекты с ними. Все ограничено функциями. И у них есть удобные функции. Мы можем проверить параметры через ключевое слово arguments. Мы можем временно прикрепить и запустить их в контексте методов других объектов. И они делают управляемые событиями подходы к вещам непристойно легкими для реализации. Короче говоря, они сделали JS абсолютным чудовищем в снижении сложности и адаптации различных реализаций самого JS (но в основном DOM API) прямо в источнике.
Переоценка моделей / практики перед принятием
Функции первого класса и динамические типы делают многие более сложные шаблоны проектирования совершенно бессмысленными и громоздкими в JS. Однако некоторые из более простых шаблонов невероятно полезны и просты в реализации, учитывая очень гибкий характер JS. Адаптеры и декораторы особенно полезны, и я нашел синглтоны полезными для сложных фабрик виджетов пользовательского интерфейса, которые также действуют как менеджеры событий для элементов пользовательского интерфейса, которые они создают.
Следуйте указаниям языка и делайте больше с меньшими затратами
Я полагаю, что один из руководителей Honchos из Java где-то утверждает, что многословие на самом деле является положительной чертой, облегчающей понимание кода всеми сторонами. Фигня. Если бы это было правдой, было бы легче читать юридический. Только писатель может сделать то, что он написал, легче для понимания, и вы можете сделать это только иногда, ставя себя на место другого парня. Итак, примите эти два правила. 1. Будьте максимально прямыми и ясными. 2. Добраться до чертовой точки уже. Выигрыш в том, что чистый, лаконичный код на несколько порядков легче понять и поддерживать, чем то, где вам нужно пройти двадцать пять уровней, чтобы перейти от триггера к реальному желаемому действию. Большинство шаблонов, которые поддерживают такие вещи в более строгих языках, на самом деле являются обходными путями для ограничений, которых нет в JavaScript.
Все податливое и все в порядке
JS, вероятно, является одним из наименее протекционистских языков в популярном использовании. Прими это. Работает нормально. Например, вы можете писать объекты с недоступными постоянными «частными» переменными, просто объявляя обычные переменные в функции конструктора, и я делаю это часто. Но это не для того, чтобы защитить мой код или его пользователей «от себя» (они все равно могли бы просто заменить его собственной версией во время выполнения). Но скорее это должно сигнализировать о намерениях, потому что предполагается, что другой парень достаточно компетентен, чтобы не хотеть манипулировать какими-либо зависимостями, и увидит, что вы не должны добиваться этого напрямую, возможно, по уважительной причине.
Нет ограничений по размеру, есть только проблемные домены
Самая большая проблема, с которой я столкнулся во всех кодовых базах Java, - это переизбыток файлов классов. Прежде всего, SOLID - это просто запутанное повторение того, что вы уже должны знать об ООП. Класс должен обрабатывать определенный набор связанных проблем. Не одна проблема с одним методом. Это просто берет старый дрянной код на func-spaghetti C только с добавлением всего бессмысленного синтаксиса классов для загрузки. Нет ограничений по размеру или методу. Если имеет смысл добавить что-то к уже длинной функции, классу или конструктору, это имеет смысл. Возьми jQuery. Это полный набор инструментов длиной библиотеки в одной функции, и в этом нет ничего плохого. Нужны ли нам все еще jQuery - это спорные вопросы, но с точки зрения дизайна,
Если Java - это все, что вы знаете, балуйтесь чем-то с синтаксисом, не основанным на C
Когда я начал возиться с Python, потому что мне понравилось то, что я слышал о Django, я научился отделять синтаксис от языкового дизайна. В результате стало проще понимать Java и C как сумму их частей проектирования языка, а не как сумму вещей, которые они делают по-разному с одинаковым синтаксисом. Приятным побочным эффектом является то, что чем больше вы понимаете другие языки с точки зрения дизайна, тем лучше вы будете понимать сильные / слабые стороны того, который вы знаете лучше всего по контрасту.
Вывод
Теперь, учитывая все это, давайте поразим все ваши проблемные моменты:
- Нет непосредственного способа найти точку входа в функцию (кроме простого текстового поиска, который может затем привести к последующим поискам методов дальше по иерархии вызовов, после двух или трех из которых вы забыли, с чего начали)
Chrome и Firebug действительно имеют функцию отслеживания вызовов. Но посмотрите также мои пункты о структуре и сохранении вещей краткими и прямыми. Чем больше вы можете думать о своем приложении как о больших хорошо инкапсулированных конструкциях, взаимодействующих друг с другом, тем легче будет понять, чья это вина, когда что-то идет не так. Я бы сказал, что это верно и для Java. У нас есть классоподобные конструкторы функций, которые идеально подходят для традиционных задач ООП.
function ObjectConstructor(){
//No need for an init method.
//Just pass in params and do stuff inside for instantiation behavior
var privateAndPersistent = true;
//I like to take advantage of function hoisting for a nice concise interface listing
this.publicAndPointlessEncapsulationMurderingGetterSetter
= publicAndPointlessEncapsulationMurderingGetterSetter;
//Seriously though Java/C# folks, stop with the pointless getter/setters already
function publicAndPointlessEncapsulationMurderingGetterSetter(arg){
if(arg === undefined){
return privateAndPersistent;
}
privateAndPersistent = arg;
}
}
ObjectConstructor.staticLikeNonInstanceProperty = true;
var instance = new ObjectConstructor();//Convention is to capitalize constructors
В моем коде я почти никогда не использую объектные литералы в {}
качестве структурных компонентов приложения, поскольку они не могут иметь внутренние (частные) переменные, и вместо этого предпочитаю резервировать их для использования в качестве структур данных. Это помогает установить ожидание, которое поддерживает ясность намерений. (если вы видите кудри, это данные, а не компонент архитектуры приложения).
- Параметры передаются в функции без возможности узнать, какие свойства и функции доступны для этого параметра (кроме фактического запуска программы, перехода к точке, в которой вызывается функция, и использования console.logs для вывода всех свойств имеется в наличии)
Опять же, посмотрите современные инструменты браузера. Но также, почему это такой облом, чтобы снова запустить программу? Перезагрузка - это то, что веб-разработчик на стороне клиента обычно делает каждые несколько минут, потому что это абсолютно ничего не стоит. Это снова, еще один момент, с которым структура приложения может быть полезна, но это один из отрицательных компромиссов JS, который вы должны выполнить свою собственную проверку, когда принудительное выполнение контрактов является критически важным (то, что я делаю только в конечных точках, подверженных другим вещам, которые моя кодовая база не делает не контролирую). ИМО, компромисс стоит своих выгод.
- Распространенное использование анонимных функций в качестве обратных вызовов, которое часто приводит к спагетти запутанных путей кода, которые вы не можете быстро перемещаться.
Да, это плохо на что-нибудь нетривиальное. Не делай этого. Назовите ваши функции, дети. Также легче отслеживать вещи. Вы можете определить, оценить (необходимо назначить) и назначить простую тривиальную функцию в строке:
doSomethingWithCallback( (function callBack(){}) );
Теперь Chrome будет иметь имя для вас, когда вы будете отслеживать звонки. Для нетривиальной функции я бы определил ее вне вызова. Также обратите внимание, что анонимные функции, назначенные переменной, все еще являются анонимными.
- И, конечно же, JSLint ловит некоторые ошибки перед выполнением, но даже это не так удобно, как наличие красных волнистых линий под вашим кодом прямо в браузере.
Я никогда не трогаю вещи. Крокфорд поделился с сообществом некоторыми хорошими вещами, но JSLint переходит грань в стилистические предпочтения и предполагает, что определенные элементы JavaScript являются плохими частями без особой причины, IMO. Обязательно игнорируйте одну вещь о классах regEx и отрицании, за которыми следуют * или +. Подстановочные знаки работают хуже, и вы можете легко ограничить повторение с помощью {}. Кроме того, игнорируйте все, что он говорит о конструкторах функций. Вы можете легко обернуть их в фабричный функционал, если вас беспокоит новое ключевое слово. CSSLint (не Крокфорда) еще хуже в плане плохих советов. Всегда берите людей, которые много выступают с солью. Иногда я клянусь, что они просто хотят установить авторитет или создать новый материал.
И опять же, вы должны отучиться от того, что вы узнали с этим беспокойством во время выполнения, которое у вас есть. (это обычное явление, которое я видел у многих разработчиков Java / C #) Если появление ошибок во время выполнения по-прежнему беспокоит вас 2 года спустя, я хочу, чтобы вы сели и перезагрузили спам в браузере, пока он не утонул. нет разделения по времени компиляции / времени выполнения (ну, во всяком случае, не видимое - JS теперь работает на JIT). Не только хорошо обнаруживать ошибки во время выполнения, но и очень выгодно так дешево и легко перезагружать спам и обнаруживать ошибки в каждой точке остановки, к которой вы попадаете.
И взломайте эти инструменты разработчика Chrome. Они встроены непосредственно в webkit. Щелкните правой кнопкой мыши в Chrome. Осмотрите элемент. Исследуйте вкладки. Там есть много возможностей для отладки с возможностью изменять код в консоли во время выполнения, что является одним из самых мощных, но менее очевидных вариантов. Отлично подходит для тестирования тоже.
С другой стороны, ошибки ваши друзья. Никогда не пишите пустое выражение catch. В JS мы не скрываем и не хороним ошибки (или, по крайней мере, мы не должны кашлять YUI / кашлять ). Мы заботимся о них. Все, что меньше, приведет к боли отладки. И если вы действительно напишите оператор catch, чтобы скрыть потенциальные ошибки в работе, по крайней мере, молча зарегистрируйте ошибку и запишите, как получить доступ к журналу.