В прошлом году я потратил на разработку <angular /> для JavaScript (клиент) и Ruby на сервере, и я полностью изменил свое мнение о динамических языках, и я хотел поделиться с вами некоторыми соображениями.
Тесты являются обязательными
Компиляторы замечательно говорят вам, что вы что-то неправильно набрали или что ваши предположения о классах неверны, но так же выполняется код. Так что, если весь мой код уже выполнен тестами, то зачем мне дополнительная проверка компилятора. Компиляция не требует прекращения тестов, но тесты требуют прекращения работы компилятора. Так что, если у вас почти 100% охват, вам не нужен компилятор, чтобы сказать, что вы что-то опечатали.
Чтобы получить почти 100% охват, сначала нужно пройти тесты, и это должно быть для вас второй натурой. Я запускаю все свои тесты JavaScript при каждом сохранении в большинстве браузеров, используя JSTestDriver, и все мои тесты выполняются за секунду. Эта мгновенная обратная связь при каждом сохранении так же хороша, как если бы Eclipse подчеркнул ваш код, что вы допустили ошибку, и поэтому я действительно не пропускаю компилятор.
Я вижу, как динамический язык может стать кошмаром, если у вас нет тестов.
Тесты легче писать
Поскольку нет компилятора, который бы беспокоил вас о типах, очень легко подделать зависимости. Ожидаете ли вы сложный класс, но вы знаете, что в своем тесте вы используете только один метод, который должен возвращать константу? Кусок пирога! Создайте безымянный объект с единственным свойством, у которого есть метод, и все готово.
Печатать много печатать
Печатание, как следует из названия, это просто много печатать.
Ява:
List<Book> books = new ArrayList<Book>();
JavaScript:
var books = [];
Посмотрите, насколько длиннее строка Java и насколько короче JavaScript. Отсутствует ли какая-либо информация? Оба говорят, что у меня есть список Книг, но один говорит это по соглашению (имена переменных, заканчивающиеся на ‘s’, являются массивами имени), где другой является явным и заставляет меня повторить себя, набрав книгу три раза и дважды Список. (Тесты, докажите, что мой код работает, компилятор не нужен.)
Плотность кода
Плотность кода в динамических языках феноменальна! Все бесконечное приведение, приведение и повторение в объявлении просто не существует, что приводит к очень плотному коду. Но я мастер Eclipse Jedi и могу генерировать всю эту многословность с помощью нескольких нажатий клавиш, поэтому ввод текста не является проблемой! Правда, но чтение / сжатие есть! 10 строк кода легче понять, чем 100, а в JavaScript эти 10 строк часто делают более 100 в Java. (Начать с 100 строк кода не умещается на моем экране сразу.) Оказывается, JavaScript все еще многословен, а CoffeeScript еще лучше!
Функции как граждан первого класса и классы с одиночными методами
Имея функции первоклассных граждан, которых можно обойти, это круто! Смотрите казнь в царстве существительных ! Функции — это глаголы, и вам нужны и глаголы, и существительные, чтобы составить предложение.
Недавно я получил письмо от кого-то, в котором указывалось, что выполнение надлежащего принципа единой ответственности часто приводило к занятиям, в которых был только один метод. Странный? Ну, на самом деле, это скрытая функция.
Закрытие функции == Внедрение в конструктор
Если Class с одним методом является функцией, то внедрение зависимости для этого класса является закрытием функции. Где создается функция, определяет ее зависимости и видимость, что хорошо решает проблему внедрения зависимостей для функций.
JavaScript так прост
Я постоянно в восторге, насколько простой JavaScript на самом деле! Я могу объяснить вам все правила JavaScript за несколько часов, чего я не могу сделать с Java. И все же, я чувствую, что JavaScript гораздо более мощный, чем Java, потому что он имеет функции граждан первого класса.
Все еще правда
Все то, о чем я говорил в своем блоге, все еще верно. Внедрение зависимостей является обязательным условием, и динамическая природа JavaScript не оставляет желать лучшего. Любой, кто утверждает, что DI предназначен только для Java и что его язык каким-то образом освобождает его от правил управления вашими зависимостями, должен больше узнать о DI. Точно так же глобальное состояние — плохая идея, и JavaScript здесь очень плохой, так как глобальный является значением по умолчанию, и вам нужно выполнить дополнительную типизацию, чтобы получить область видимости проперов, то же самое касается функций и их привязки по умолчанию к глобальному состоянию. Плохой JavaScript, плохой! Отделение проводки от логики все еще остается верным, и никакое количество исправлений обезьяны не оставит вас в здравом уме в долгосрочной перспективе.
Куда ушел наследство?
Я написал 10 000 строк JavaScript, и мне еще предстоит столкнуться с необходимостью наследования. Куда это делось? Правильное использование наследования == полиморфное поведение, но это можно сделать с помощью утиной типизации, просто внедрив правильные методы.
Масштабирование команды
Я слышал это много раз раньше: мне нравится (вставьте здесь свой динамический язык) первые 1000 строк, чем я скучаю по своим типам. Что ж, я написал 10 000 строк и ни разу не пропустил компилятор, совсем наоборот, я научился ненавидеть, когда вернулся в Java и компилятор мешает. Так почему мой опыт отличается? Одним словом: тесты! Я очень серьезно отношусь к тестированию, как и мои товарищи по команде! Пока у вас есть тесты, отсутствие компилятора не является проблемой, и код прекрасно масштабируется для большего количества членов команды. Но можно утверждать, что он лучше масштабируется:
- Меньше кода, чтобы поддерживать, писать и понимать
- Если вы не можете этого понять, просто перепишите его, после всего лишь нескольких сотен строк, сколько времени это займет у вас?
JavaScript на сервере
Разработка веб-приложений означает, что вы должны быть опытными как в Java, так и в JavaScript, но давайте исправим эту проблему, перенеся JavaScript на сервер. Node.js — прекрасный пример этого, и мне это нравится.
Неблокирующий API
Неблокирующее API — это гениальный штрих! Короче говоря, это делает невозможным писать медленные тесты. В конце концов, как можно замедлить тестирование, если все вызовы методов возвращаются немедленно? Вот почему я могу выполнить 400 тестов за 500 мс при каждом сохранении.
От http://misko.hevery.com/2010/04/07/move-over-java-i-have-fallen-in-love-with-javascript