HOP core language == Presentation == This document presents the core constructions of the HOP programming language. It does not present the APIs which are already presented in the ++API++ tab. ~~ HOP is functional expression based programming language. That is: * All HOP expression as a value. * Functions are first class values. They can be passed as argument, returned as result, or stored in data structure. ~~ HOP uses a lexical scoping discipline, that is the functions capture their definition environment for their free variables. ~~ HOP is safe because it checks types and array bounds. Contrary to languages such as [[http://caml.inria.fr/|ML]], HOP checks types at runtime. == Syntax == ~~ In this text we use the classical conventions. The sign ,( "+") denotes a non empty repetition. The sign ++*++ denotes a possibly empty repetition. The sign ++?++ denotes an optional occurrence. The sign ++|++ denotes the alternative. ~~ HOP expressions are either atoms, quotes, or lists. := | | | An atom is a syntactic elements described by the following grammar: := | | | | | | #unspecified := [a-zA-Z<>/?|!@%^&*-_=+][a-zA-Z0-9<>/?|!@%^&*-_=+]* := : := " + " := "any character but " and \" | \ [\"tnr] := # \ "a character" | #\Newline | #\Space | #\Return | #\Tab := #t | #f Hop supports //texts//. A text is made of a list of strings. A text is actually a syntactic shorthand for building list of strings. := | := [ ... ] := { ... } Inside all characters are left as is with two exceptions: * the character ,(begin "]") must escaped as ,(begin "\\]"), * the sequence ,(begin ",(") is an escape operator. It introduce an Hop expression inside a text. Inside all characters are left as is with two exceptions: * the characters ,(begin "{") and ,(begin "}") that are included in the text but must be balanced. The text is ended when the parse reads a closing bracket matching the one that has opened the text construction. * the character ,(begin "$") is an escape operator. It introduces an Hop expression inside a text. The sequence ,(begin "$$") introduces a single ,(begin "$") sign in the text construction. Quotes are: := ' | := '#(*>) Lists are: := (*) In addition to these syntactic elements, server-side expressions may use //client-side// embedding: := | ~ Symmetrically, client-side expressions may use //server-side// embedding: := | $ == Definitions == HOP supports definitions of variables, functions, and services: := | | := (define ) := (define ( *) ) := (define-service ( *) ) == Basic constructions == The sequence of HOP expressions is: := (begin ...) The alternative is: := (if ?) HOP supports derivative conditional constructions: := (cond (( )+)) := (case ((+ )+)) Local variables are introduced with the ++let++ constructions: := | | := (let (*) ) := (let* (*) ) := (letrec (*) ) := | ( ) The ++let++ construction binds independent variable. The ++let*++ is equivalent to a cascade of nested ++let++s. The ++letrec++ allows recursive definitions of lexical variables. Anonymous functions are introduced by ++lambda++ expression: := (lambda (*) ) Loops are either defined with //named let// or anonymous functions: := (let (*) ) Function applications are defined as: := ( *) Anonymous services are introduced by the ++service++ form: := (service [:ttl ] [:timeout ] [:url ] (*) ) == Conditional compilation == Conditional compilation are managed in HOP by the ++cond-expand++ form: := (cond-expand ( )+) := else | | (not ) | (or +) | (and +) := symbol Hop defines the following features: * bigloo * hop * hop- (//i.e.//, hop-2.0.0) * hop- (//i.e.//, hop-2.0.x) In addition, client-side defines additional features that allows source code to behave differently on the server and on the client: * scheme2js See ,( ( "Conditional Compilation") "condexpand.wiki") for additional details. == Modules == Modules structure HOP weblet. Server and client codes may use modules. A module //export// variables, functions, and classes. A module might //import// another module. In that case, it may access to the imported variables, functions, and classes. ~~ The syntactic structure of a module is as follows: (module + ...) * A single file cannot contain more than one module. The syntax for the clauses is: := | | | | | := (import +) | | := | ( ) := ~(import +) can only be used by server code := $(import +) can only be used by client code := (library +) := (export +) := | | := := (+) | (generic +) := (class ) := | ( +) := read-only | (default ) ~~ Here is an example of a module named ++foo++ that uses the library ++ssl++, that imports the module named ++bar++, and that exports the function ++fun-foo++, the variable ++var-foo++, and the class ++class-foo++. (module foo (library ssl) (import bar) (export (fun-foo x) var-foo (class class-foo (name read-only) (x (default 0)) (y (default 0))))) === Module Access File === ~~ Hop is different from languages such as C where a module is defined by a file. For Hop, the module name is not necessarily the name of the file where the text of the module is written and modules can even be split across several files. ~~ Since modules are defined independently of files, it is necessary to make a link between a module and its files and there are two ways of doing this. Choosing an import clause where the file-names are specified or creating a "module access file". Such a file must contain only one ++list++, each element of the list being of the form: (module-name "file-name" ... "file-name") ~~ By default Hop checks if a file named ++.afile++ exists. If it exists it is loaded as a module access file. ~~ Note: The Bigloo distribution contains a tool, ++bglafile++, that can automatically build a "module access file". See the manpage for ++bglafile++ for details. === Mixer server and client modules === ~~ Since Hop-2.0.x, servers and clients may mutually import modules. That is, server modules may import client modules to access to client functions and variables when producing a HTML tree. Respectively, client modules may import server modules, for instance, for accessing services from client code. The following example illustrate this mutual imports. ~~ The following server module defines a weblet drawing chart: (module foo-server (import (gchart "http://localhost:8080/hop/weblets/download?weblet=gchart-api-1.0.0.hz")) (export img pre) ~(import foo-client)) (define types '(bhs bvs bhg bvg p p3 pc chp v s r rs)) (define tnum 0) (define (new-url) (let ((len (length types))) (set! tnum (+fx tnum 1)) (if (>=fx tnum len) (set! tnum 0)) (google-chart :colors '("a25cff" "f72f2b" "253c81" "c62f6d" "522e81" "f79326" "f7d93a" "aef742" "69f7ab" "3df7ec") :type (list-ref types tnum) :data (map (lambda (l) (cons (symbol->string l) (random 100))) types)))) (define url (new-url)) (define img ( :id "img" :src url :title "An image")) (define pre (
 :id "pre" :style "font-size: 70%" url))
  
  (define-service (foo)
     (
        ( :jscript (service-resource foo "foo.scm"))
        (
         (