Ваша первая чашечка CoffeeScript : Часть 1. Приступаем к работе

Сегодня много говорят о CoffeeScript, новом языке программирования на базе JavaScript. CoffeeScript отличается четким синтаксисом, который придется по душе сторонникам Python или Ruby. Он содержит также множество функциональных возможностей, навеянных такими языками программирования, как Haskell и Lisp. CoffeeScript компилируется в эффективный код JavaScript, и его можно использовать не только для выполнения JavaScript в Web-браузере, но и с такими технологиями, как Node.js для серверных приложений. В этой первой части цикла из четырех статей читатели познакомятся с CoffeeScript и узнают о том, какие выгоды он сулит разработчикам. Мы установим компилятор CoffeeScript и будем использовать его для создания кода, который можно исполнять в браузере или на сервере.

Майкл Галпин, инженер по программному обеспечению, Vitria Technology

Майкл Галпин (Michael Galpin) имеет учёную степень по математике в Калифорнийском Технологическом институте. Он является Java-разработчиком с конца 90-х гг. и работает инженером по программному обеспечению в Vitria Technology, в Саннивейл, Калифорния.



19.07.2012

Введение

Язык программирования CoffeeScript построен поверх JavaScript и компилируется в эффективной код JavaScript, который можно выполнять в Web-браузере или с такими технологиями, как Node.js для серверных приложений. Процесс компиляции, как правило, прост, а получаемый в результате код JavaScript соответствует многим рекомендациям. В этой статье рассматриваются особенности языка программирования CoffeeScript. После установки CoffeeScript и запуска компилятора мы выполним простой пример с использованием CoffeeScript на Web-странице.

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


Преимущества CoffeeScript

Часто используемые сокращения

  • NPM: Node Package Manager
  • REPL: Read-Evaluate-Print-Loop

JavaScript — самый важный язык программирования наших дней. Это язык браузеров, который все чаще встречается также в настольных и мобильных приложениях. С ростом популярности Node.js JavaScript стал жизнеспособным инструментом и для серверных и системных приложений. Некоторые разработчики решительно отвергают JavaScript, во многом из-за его алогичного синтаксиса и несовместимых реализаций. Однако виртуальные машины JavaScript становятся все более стандартизованными. Проблема же алогичного синтаксиса может быть решена на следующем витке развития JavaScript: в новом стандарте ECMAScript.next, разрабатываемом под заметным влиянием CoffeeScript. Однако до тех пор пока новый стандарт не будет согласован и реализован в популярных виртуальных машинах, синтаксис JavaScript оставляет много места для совершенствования.

CoffeeScript – соблазнительный вариант для всех, кто пишет программы для среды исполнения JavaScript. С точки зрения синтаксиса JavaScript очень разнороден. В нем много от языков функционального программирования и много навеянного, например, языком Scheme. Однако у Scheme чрезвычайно простой синтаксис, построенный на s-выражениях. JavaScript разделяет многие идеи языка Scheme, но не его синтаксис. Вместо этого в JavaScript используется Cи-подобный синтаксис. Результатом стал язык, позаимствовавший идеи функциональных языков, но с многословным синтаксисом, лишенным естественных конструкций для выражения этих идей. Например, JavaScript допускает функции высокого порядка, такие как функции, входные параметры которых включают другие функции. Это полезное и мощное средство, отсутствующее во многих языках. Однако синтаксис JavaScript не всегда элегантен, как показано в листинге 1.

Листинг 1. Неприглядный JavaScript
pmb.requestPaymentInfo('type', function(info){
    $('result').innerHTML = info.name;
});

В этом примере много балласта – круглые скобки, запятые, фигурные скобки, точки с запятой и ключевые слова языка, ― без которого можно было бы легко обойтись.

JavaScript в основном используется как язык клиентской части Web-приложений. Все платформы настольных и мобильных приложений, такие как Cocoa, Windows® Forms и Android, ― объектно-ориентированные платформы. Нельзя сказать, что парадигма объектно-ориентированных языков идеально подходит для всего, но для приложений с графическим интерфейсом пользователя она хороша. JavaScript — это тоже объектно-ориентированный язык с наследованием, но это прототипичный язык – он не основан на классах, как языки, используемые большинством платформ приложений. Поэтому программирование приложений на JavaScript может оказаться весьма громоздким.

CoffeeScript устраняет недостатки JavaScript. Он:

  • предоставляет простой синтаксис с меньшим количеством балласта, такого как скобки и запятые;
  • использует пробелы как способ организации блоков кода;
  • обеспечивает простой синтаксис для выражения функций;
  • обеспечивает наследование на основе классов (это не обязательно, но при разработке приложений может оказаться весьма полезным).

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


Предварительные требования

Как уже упоминалось, CoffeeScript можно использовать для написания серверных и системных приложений, которые работают поверх Node.js. Однако связь между CoffeeScript и Node.js гораздо глубже. Чтобы установить CoffeeScript, нужно сначала установить Node.js, потому что:

  • CoffeeScript распространяется как пакет Node.js с помощью менеджера пакетов Node ― NPM;
  • CoffeeScript нужно компилировать. Сам компилятор написан на CoffeeScript и, следовательно, для компиляции требуется среда исполнения JavaScript. Для этого идеально подходит виртуальная машина JavaScript V8, лежащая в основе Node.js.

Чтобы следовать примеру из этой статьи, нужно установить Node.js.


Установка

Хотелось ли вам когда-нибудь запустить JavaScript из командной строки? Мне - нет, но не исключено, что CoffeeScript изменит это положение. Node.js позволяет запустить JavaScript из командной строки или в рамках исполняемого сценария. Благодаря этой важной особенности Node.js код CoffeeScript можно выполнять из командной строки, предоставив среду исполнения, необходимую для работы компилятора CoffeeScript (который написан на CoffeeScript).

Первый шаг заключается в установке Node.js. Существует несколько способов установки: можно скомпилировать исходный код или запустить одну из программ установки, которые имеются во многих системах. Выполните из командной строки команду node -v, чтобы убедиться, что Node.js установлен и доступен.

К Node.js прилагается бонус: менеджер пакетов Node (NPM). Выполнив из командной строки команду npm -v, чтобы убедиться, что NPM установлен и доступен, его можно использовать для установки CoffeeScript.

  1. Выполните из командной строки: npm install --global coffee-scrip.

    Флаг --global делает CoffeeScript доступным в рамках всей системы, а не только для определенного проекта.

  2. Команда npm должна вывести что-то вроде /usr/bin/coffee -> /usr/lib/node_modules/coffee-script/bin/coffee.

    NPM создает ярлык в папке /usr/bin, так что теперь исполняемый код coffee находится по нужному пути. Это компилятор и интерпретатор CoffeeScript.

  3. Чтобы убедиться, что исполняемый файл coffee находится по нужному пути, выполните из командной строки: coffee -v.

Еще один, последний шаг гарантирует правильную настройку среды CoffeeScript. Чтобы сделать CoffeeScript доступным для любого запущенного процесса Node.js, необходимо добавить его в NODE_PATH. При обнаружении неопознанных функций Node.js ищет модули (библиотеки) в NODE_PATH.

Например, в этой статье Node.js используется главным образом в качестве среды выполнения для исполняемых файлов CoffeeScript. Самый простой подход ― просто добавлять в NODE_PATH все модули NPM. Чтобы разыскать модули NPM, введите npm ls -g. Необходимо добавить переменную среды, указывающую NODE_PATH на эту папку. Например, если npm ls -g выдает /usr/lib, то модули расположены в папке /usr/lib/node_modules. Чтобы задать переменную среды NODE_PATH, выполните: export NODE_PATH=/usr/lib/node_modules.

Можно упростить задачу еще больше, вставив предыдущую команду в сценарий запуска (например, ~/.bash_profile). Для проверки изменений запустите оболочку Node.js, выполнив Node, а затем введите require('coffee-script'). Оболочка Node.js должна загрузить библиотеку CoffeeScript. Если это происходит, то среда CoffeeScript готова к работе. Теперь можно приступить к изучению CoffeeScript, начиная с компилятора.


Компилятор

Чтобы запустить компилятор CoffeeScript, достаточно ввести команду coffee -c, которая запускает процесс CoffeeScript read-evaluate-print-loop (REPL). Для выполнения компилятора нужно передать ему файл CoffeeScript, который следует скомпилировать. Создайте файл с именем cup0.coffee и вставьте в него содержимое листинга 2.

Листинг 2. Cup 0
for i in [0..5]
    console.log "Hello #{i}"

Легко догадаться, что делают две строки кода в листинге 2. Листинг 3 демонстрирует результат выполнения coffee cup0.coffee.

Листинг 3. Запуск вашего первого сценария CoffeeScript
$ coffee cup0.coffee 
Hello 0
Hello 1
Hello 2
Hello 3
Hello 4
Hello 5

Чтобы получить более полное представление о том, что происходит, попробуйте запустить компилятор. Введите команду coffee -ccup0.coffee, которая создаст файл с именем cup0.js. В листинге 4 показано содержимое cup0.js.

Листинг 4. Код JavaScript Cup 0
(function() {
    var i;
    for (i = 0; i <= 5; i++) {
        console.log("Hello " + i);
    }
}).call(this);

Синтаксис CoffeeScript элегантнее, чем у JavaScript, но он компилируется в очень простой, логичный код JavaScript. Вы можете спросить, зачем весь код упакован в функцию. Дело в том, что JavaScript поддерживает определение области только на уровне функции. Заключая все в функцию, мы гарантируем, что переменная будет ограничена только этой функцией и не станет глобальной (и не заменит существующую глобальную переменную).

Откройте новый файл с именем cup1.coffee и введите более сложный код, приведенный в листинге 5.

Листинг 5. Cup 1
stdin = process.openStdin()
stdin.setEncoding 'utf8'

stdin.on 'data', (input) -> 
    name = input.trim() 
    process.exit() if name == 'exit' 
    console.log "Hello #{name}"
    console.log "Enter another name or 'exit' to exit"
console.log 'Enter your name'

Программа из листинга 5 предлагает пользователю ввести свое имя, а затем приветствует его соответствующим образом. В JavaScript нет встроенных библиотек для чтения из стандартного устройства ввода, но в Node.js такие библиотеки есть. Это еще одно преимущество симбиоза CoffeeScript/Node.js. В таких языках, как Cи, чтение из стандартного устройства ввода представляет собой блокирующий вызов. До тех пор, пока не закончится чтение из стандартного устройства ввода, не может выполняться никакой код. Те, кто знаком с Node.js, знают, что так нельзя; Node.js не позволяет блокировать ввод-вывод. Вместо этого необходимо зарегистрировать функцию обратного вызова с помощью stdin.on.

Выполнив командуcoffee -c cup1.coffee, вы увидите код JavaScript, созданный компилятором CoffeeScript, как показано в листинге 6.

Листинг 6. Код JavaScript Cup 1
(function() {
    var stdin;
    stdin = process.openStdin();
    stdin.setEncoding('utf8');
    stdin.on('data', function(input) {
        var name;
        name = input.trim();
        if (name === 'exit') { 
            process.exit();
        }
        console.log("Hello " + name);
        return console.log("Enter another name or 'exit' to exit");
    });
   console.log('Enter your name');
}).call(this);

Функция Stdin.on использует типичный формат привязки событий. Вы указываете тип события ('data'), которые нужно отслеживать, а затем присваиваете ему функцию обратного вызова, которая будет выполняться, когда событие произойдет. В скомпилированном коде JavaScript просматривается типичный многословный сценарий JavaScript для создания встроенной функции и ее передачи другой функции. Сравните его с эквивалентным кодом CoffeeScript. Все эти скобки, фигурные скобки, точки с запятой и ключевые слова больше не нужны!

Теперь, когда вы умеете компилировать программы на CoffeeScript, рассмотрим одну из самых полезных функций CoffeeScript: REPL.


Функция REPL

Функция REPL ― это стандартный инструмент, присутствующий во многих языках программирования, особенно из числа функциональных языков. REPL ― это эквивалент Ruby IRB. Чтобы запустить CoffeeScript REPL, просто введите coffee. Давайте поэкспериментируем с этой функцией CoffeeScript и решим простые задачи, показанные в листинге 7.

Листинг 7. Использование REPL
coffee> nums = [1..10]
[ 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 ]
coffee> isOdd = (n) -> n % 2 == 1
[Function]
coffee> odds = nums.filter isOdd
[ 1, 3, 5, 7, 9 ]
coffee> odds.reduce (a,b) -> a + b
25

Каждый раз, когда в функцию REPL вводится выражение, она вычисляет его, распечатывает результат и ждет следующего выражения. В примере определяется переменная с именем nums и диапазоном значений от 1 до 10. REPL распечатает значение только что определенной переменной. Эта функция может сразу же оказаться полезной. Допустим, вы не помните, как вы определили диапазон ― как включающий (включая последнее число – в данном случае, 10) – или исключающий. REPL покажет вам, что значение 10 включено, так что это включающий диапазон. Если нужен исключающий диапазон, достаточно написать: nums = [1... 10].

Затем определяется функция isOdd. У CoffeeScript весьма лаконичный синтаксис объявления функций, и это хорошо согласуется с функциональным характером JavaScript. В этом примере REPL просто показывает [Function], давая понять, что переменная isOdd эквивалентна функции. Затем объявляется новая переменная, odds. Чтобы получить значение odds, мы вызываем функцию фильтра по nums и передаем ее в isOdd. Это приводит к созданию нового массива, элементы которого при передаче в isOdd должны давать значение true. К odds применяется функция reduce. При передаче функции значение каждого элемента массива добавляется к предыдущей сумме значений, и REPL отображает результирующую сумму 25.

В следующем разделе рассматриваются тема, близкая и дорогая каждому программисту на JavaScript: создание сценариев для Web-браузера.


Простой пример Web-программы

Мы показали, как писать файлы CoffeeScript и компилировать их в код JavaScript, который затем, конечно же, можно использовать в Web-приложении. Для целей разработки существует более простой способ. Компилятор CoffeeScript может выполняться внутри браузера, что позволяет использовать CoffeeScript непосредственно на Web-странице. Однако если вы создаете высокопроизводительные Web-приложения, такой способ использования CoffeeScript не рекомендуется. Компилятор CoffeeScript ― это большой файл, и необходимость компилировать CoffeeScript динамически, конечно, замедляет работу. Существует простой способ разработки приложения с указанием явного "пути к рабочему коду".

CoffeeScript ― это не инструментарий или среда разработки для JavaScript. Это язык программирования и, следовательно, он не содержит большого количества удобных DOM-функций. Однако CoffeeScript можно использовать со своим любимым инструментарием. Наиболее распространенное сочетание – это CoffeeScript с jQuery. В листинге 8 приведена простая Web-страница, разработанная с использованием jQuery и CoffeeScript.

Листинг 8. CoffeeScript на Web-странице
<html>
<head>
    <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.4.2/jquery.min.js">
</script>
    <script
 src="http://jashkenas.github.com/coffee-script/extras/coffee-script.js">
 </script>
    <script type="text/coffeescript">
        gcd = (a,b) -> if (b==0) then a else gcd(b, a % b)
        $("#button").click -> 
            a = $("#a").val() 
            b = $("#b").val() 
            $("#c").html gcd(a,b)
    </script>
</head>
<body>
    A: <input type="text" id="a"/><br/>
    B: <input type="text" id="b"/><br/>
    <input type="button" value="Calculate GCD" id="button"/> <br/>
    C: <span id="c"/>
</body>
</html>

Для загрузки jQuery Web-страница использует библиотеку Google Ajax. Библиотека компилятора CoffeeScript загружается из хранилища Github создателя CoffeeScript Джереми Ашкенаса (см. раздел Ресурсы). Затем в коде следует блок сценария. Это блок сценария типа text/coffeescript, а не text/javascript ― так компилятор CoffeeScript "узнает", что содержимое нужно скомпилировать. Затем сценарий создает функцию gcd, вычисляющую наибольший общий делитель двух целых чисел. Для создания обработчика кнопки на странице используется jQuery. Этот обработчик выдает значения двух входных строк и передает их функции gcd. Результат возвращается на Web-страницу. $(), val() и html() - все это функции jQuery, но их можно легко применять с CoffeeScript, пользуясь преимуществами четкого синтаксиса CoffeeScript.


Заключение

В этой статье содержится краткий обзор CoffeeScript. Теперь, когда среда разработки готова, можно приступать к исследованию CoffeeScript с помощью REPL. Вы научились использовать компилятор, увидели, какой код JavaScript он выдает, а также научились писать код CoffeeScript и исполнять его прямо на Web-страницах. Приведенные примеры дают представление о синтаксисе CoffeeScript, правда, как правило, без подробных объяснений.

Во второй статье этого цикла мы углубимся в детали ключевых идей CoffeeScript.


Загрузка

ОписаниеИмяРазмер
Исходный код примера для статьиcs1.zip1 КБ

Ресурсы

  • Оригинал статьи
  • Just what is Node.js? (developerWorks, май 2011 г.): об интерпретаторе JavaScript на стороне сервера Node, меняющем представление о том, как должен работать сервер.
  • Node.js: отправная точка для дальнейшего изучения приложения.
  • Use Node.js as a full cloud environment development stack (developerWorks, апрель 2011 г.): статья о том, как комбинировать Node.js с облачными технологиями.
  • High-performance web development with Google Web Toolkit and Eclipse (developerWorks, октябрь 2009 г.): идея компиляции в код JavaScript не нова, и поклонникам языка программирования Java следует прочесть эту статью.
  • All aboard! An introduction to Rails 3 (developerWorks, март 2010 г.): теперь CoffeeScript входит в состав Ruby on Rails. В этой статье можно прочесть и о других новых возможностях Rails.
  • CoffeeScript на Github: отправная точка для изучения CoffeeScript.
  • Create Ajax applications for the mobile web (developerWorks, март 2010 г.): дополнительные сведения об использовании Ajax в мобильных Web-приложениях.

Комментарии

developerWorks: Войти

Обязательные поля отмечены звездочкой (*).


Нужен IBM ID?
Забыли Ваш IBM ID?


Забыли Ваш пароль?
Изменить пароль

Нажимая Отправить, Вы принимаете Условия использования developerWorks.

 


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

Вся введенная информация защищена.

Выберите имя, которое будет отображаться на экране



При первом входе в developerWorks для Вас будет создан профиль и Вам нужно будет выбрать Отображаемое имя. Оно будет выводиться рядом с контентом, опубликованным Вами в developerWorks.

Отображаемое имя должно иметь длину от 3 символов до 31 символа. Ваше Имя в системе должно быть уникальным. В качестве имени по соображениям приватности нельзя использовать контактный e-mail.

Обязательные поля отмечены звездочкой (*).

(Отображаемое имя должно иметь длину от 3 символов до 31 символа.)

Нажимая Отправить, Вы принимаете Условия использования developerWorks.

 


Вся введенная информация защищена.


static.content.url=http://www.ibm.com/developerworks/js/artrating/
SITE_ID=40
Zone=Web-архитектура, Open source
ArticleID=826494
ArticleTitle=Ваша первая чашечка CoffeeScript : Часть 1. Приступаем к работе
publish-date=07192012