haxenode is nodejs written in haxe

fork me on github!

node.js

// example.js
var http = require('http'); var server = http.createServer( function (req, res) { res.writeHead(200, {'Content-Type': 'text/plain'}); res.end('Hello World\n'); } ) server.listen(1337, "127.0.0.1"); console.log('Server running at http://127.0.0.1:1337/');

run

# in terminal
$ node example.js
Server running at http://127.0.0.1:1337/

haxenode

// Haxenode.hx
import js.Node; class Haxenode { public static function main() { var server = Node.http.createServer( function( req:NodeHttpServerReq, res:NodeHttpServerResp){ res.setHeader("Content-Type","text/plain"); res.writeHead(200); res.end('Hello World\n'); } ); server.listen(1337,"localhost"); trace( 'Server running at http://127.0.0.1:1337/' ); } }

compile & run

# in terminal
$ haxe -lib nodejs -D nodejs -js haxenode.js -main Haxenode
$ node haxenode.js
Server running at http://127.0.0.1:1337/

What is haxenode?

+All the benefits of Node.js

event-driven, non-blocking design. Use npm and many open-source node.js libraries and frameworks.

What is Strong Typing?

The haxe compiler uses static type checking at compile-time so you have a stronger guarantee of the application's behavior at run-time. Haxe uses several kinds of types.

  • Class
  • Enum

    has a finite number of constructors

  • Dynamic

    skips compile-time type-checking

  • Typedef

    Define a structure or long type to reuse throughout your applications.

  • Function

    Define function types as variables.

  • Extensions

    Extends either a typedef or a class on-the-fly.
    Or create cascading typedefs.

What is Inlining?

The main advantage of using “inline” is that you can use as many variables as you want without slowing down your code with these variables accesses since the value is directly replaced in the compiled/generated code.

// Inlining Static Variables
class Test { static inline var WIDTH = 500; // type Int inferred static function main() { trace(WIDTH); // variable is replaced with 500 at compile-time } }

The principle is the same for a method. The less expensive function call is the one that is never done. In order to achieve that for small methods that are often called, you can “inline” the method body at the place the method is called.

// Inlining Methods
class Point { public var x : Float; public var y : Float; public function new(x,y) { this.x = x; this.y = y; } public inline function add(x2,y2) { return new Point(x+x2,y+y2); } } class Test { public static function main() { var p = new Point(1,2); var p2 = p.add(2,3); // is the same as writing : var p2 = new Point(p.x+2,p.y+3); } }

What is an Interface?

In object-oriented languages the term “interface” is often used to define an abstract type that contains no data, but exposes behaviors defined as methods. A class having all the methods corresponding to that interface is said to implement that interface. Furthermore, a class can implement multiple interfaces, and hence can be of different types at the same time.

An interface is hence a type definition; anywhere an object can be exchanged (in a function or method call) the type of the object to be exchanged can be defined in terms of an interface instead of a specific class. This allows later code to use the same function exchanging different object types; hence such code turns out to be more generic and reusable.

cite: http://en.wikipedia.org/wiki/Interface_(computing)

What is Type Inference?

Type Inference means that the type information is not only checked in the program, it's also carried when typing, so it doesn't have to be resolved immediately. For example a local variable can be declared without any type (it will have the type Unknown) and when first used, its type will be set to the corresponding one.

Type Inference enables the whole program to be strictly typed without any need to put types everywhere. In particular, local variables do not need to be typed, their types will be inferred when they are first accessed for reading or writing

var loc; type(loc); // print Unknown<0> loc = "hello"; type(loc); // print String

What are Generics?

A class can have several type parameters that can be used to get extensible behavior.

You can define your own parameterized classes with several type parameters for your own usage when you need it.

class GenericTest<T> { private var something:T; public function putSomething(value:T):T{ something = value; return something; } public function getSomething():T { return something; } }
// Generic Factory Method example by hhoelzer
class Item<T> { public var value:T; // factory method public static function create <T> ():Item<T> { return new Item<T>(); } private function new () {} // private constructor } // test it
class Main { public static function main () { \* this works because of type-inference, the compiler knows that the return type must be of type Item<Int>*/ var myItem:Item<Int> = Item.create(); myItem.value = 10; // works trace(myItem.value); // 10 // complex type example var myItem2:Item<Array<Int>> = Item.create(); myItem2.value = [1, 2, 3]; // works too trace(myItem2.value); // [1,2,3] } }

What is a Package?

Packages are used to organize and contain classes in namespaces to prevent collisions and group functionally similar files together.

the class haxe.unit.TestCase
belongs to package haxe.unit
and the class file is located in haxe/unit/TestCase.hx
// in osx: /usr/lib/haxe/std/haxe/unit/TestCase.hx

What is a Class?

In object-oriented programming, a class is a construct that is used as a blueprint to create instances of itself – referred to as class instances, class objects, instance objects or simply objects. A class defines constituent members which enable these class instances to have state and behavior. Data field members (member variables or instance variables) enable a class object to maintain state. Other kinds of members, especially methods, enable a class object's behavior. Class instances are of the type of the associated class.

cite: http://en.wikipedia.org/wiki/Class_(computer_programming)

What is a Macro?

Some languages features such as C #define enable the user to define syntax shortcuts. They are useful to perform some pseudo-code-generation, but at the same time allow to modify the syntax of the language, making the code unreadable for other developers.

The haxe macro system allows powerful compile-time code-generation without modifying the haxe syntax.

Macros are defined with the @:macro Metadata

// MyMacro.hx
import haxe.macro.Expr; class MyMacro { @:macro public static function getDate() { var date = Date.now().toString(); var pos = haxe.macro.Context.currentPos(); return { expr : EConst(CString(date)), pos : pos }; } } // Test.hx
class Test { static function main(){ var now = MyMacro.getDate(); // String is inferred trace(now); // print the Date and time this file was compiled. } }

Note: unlike inline functions you can do actual code generation inside the macro, before it gets compiled.

I highly recommend reading more about this feature if you are new to it, it is very powerful.

What is an Enum?

Enums are different to classes and are declared with a finite number of constructors.

When you want to ensure that only a fixed number of values are used then enums are the best thing since they guarantee that other values cannot be constructed.

enum Color { red; green; blue; } class ColorTools { static function toInt( c : Color ) : Int { return switch( c ) { case red: 0xFF0000; case green: 0x00FF00; case blue: 0x0000FF; } } }

What is an Iterator?

An iterator is an object which follows the Iterator typedef (The type T is the iterated type) :

typedef Iterator<T> = { function hasNext() : Bool; function next() : T; }

You can use the for syntax in order to execute iterators. The simplest iterator is the IntIter iterator which can easily be built using the operator ... (three dots). For example this will list all numbers from 0 to 9 :

for( i in 0...10 ) { trace(i); } // Or the usual for loop :
for( i in 0...arr.length ) { foo( arr[i] ); } // Same as :
for( item in arr ) { foo( item ); }

What is Conditional Compiling?

Sometimes you might want to have a single library using specific API depending on the platform it is compiled on. At some other time, you might want to do some optimizations only if you turn a flag ON. For all that, you can use conditional compilation macros (AKA preprocessor macros)

If the following example was compiled with -js out.js -D nodejs
then starting the compiled javascript file with the node command will echo “hello javascript!” and “hello node.js!” to the console.

// nested conditional example:
#if js // haxe code for javascript target js.Lib.alert(“hello javascript!”); #if nodejs // haxe code specific to nodejs Node.console.log(“hello node.js!”); #else // compile flag -D nodejs was not set #end #elseif php // haxe code specific to php target php.Lib.println(“hello php!”); #else // do something else #end

// multiplatform code example:
#if flash8 // haxe code specific for flash player 8
#elseif flash // haxe code specific for flash platform (any version)
#elseif js // haxe code specific for javascript plaform
#elseif neko // haxe code specific for neko plaform
#else // do something else
#error // default: “Not implemented on this platform” // or set your own error message #error “Custom error message” #end

Why use haxe?

You can create apps using a single unified programming language.

  • Use existing haxe &
    JavaScript code


    You can take advantage of the many other haxe, JavaScript, and node.js libraries such as JQuery, express, & mongo db. including many others from haxelib.

  • JavaScript2
    (ECMA4) features


    JavaScript2 promised a lot of great features for the future. haxe provides a very similar experience now & is fully compatible with current browsers.

  • Elegant Remoting
    between platforms


    Pass objects between different platforms using remoting classes from the same codebase. Successful de-serialization makes remoting between platforms elegant and fast.

  • Benefits type checking


    Strict type checking & compile-time checks allows you to catch errors before testing in the browser or vm. This means a faster workflow for dynamically typed targets (like JavaScript).

  • ECMA style programming


    ECMA style programming for client-side, server-side & desktop. The haxe syntax is familiar to those coming from ActionScript and JavaScript.

  • Extremely fast compiling


    compile time benchmarks:

    haxenode.org
    Total time : 0.197s haxenode.org/javascripts/script.js
    Total time : 0.109s

Install haxenode

Install nodejs with haxelib

# Setup haxelib if you haven't done so already
$ haxelib setup
Please enter haxelib repository path with write access Hit enter for default (/usr/lib/haxe/lib) Path : # [Return]
haxelib repository is now /usr/lib/haxe/lib/

# install nodejs using haxelib
$ haxelib install nodejs

# (optional) check that nodejs was installed successfully
$ haxelib list
... nodejs: 0.6 ...