diff --git a/.gitignore b/.gitignore
index 04cf312f..82648dbd 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,8 +1,3 @@
-.*
-apps
-db/*
-lib/ext
-modules/
server.properties
classes/*
launcher.jar
diff --git a/.gitmodules b/.gitmodules
index efd48c66..e69de29b 100644
--- a/.gitmodules
+++ b/.gitmodules
@@ -1,9 +0,0 @@
-[submodule "modules"]
- path = modules
- url = ./modules
-[submodule "swarm"]
- path = swarm
- url = ./swarm
-[submodule "apps"]
- path = apps
- url = ./apps
diff --git a/modules/README b/modules/README
new file mode 100644
index 00000000..8a0ec3d4
--- /dev/null
+++ b/modules/README
@@ -0,0 +1,17 @@
+
HelmaLib is organized into two groups of modules:
+
+
+- modules/core which contains extensions to core JavaScript types such as
+Object, Array, or Date.
+- modules/helma which provides new functionality to JavaScript, usually by
+wrapping a Java library.
+
+
+To use a HelmaLib module in your Helma application, you need to add it to the
+app's repositories. The simplest way to do so is by using the app.addRepository()
+function:
+
+ app.addRepository("modules/helma/Search.js");
+
+If you are looking for more Helma libraries, be sure to check out the
+Jala project!
diff --git a/modules/core/Array.js b/modules/core/Array.js
index f709c3c0..1e523b3f 100644
--- a/modules/core/Array.js
+++ b/modules/core/Array.js
@@ -23,7 +23,6 @@
* @addon
*/
-
/**
* Check if this array contains a specific value.
* @param {Object} val the value to check
diff --git a/modules/core/Filters.js b/modules/core/Filters.js
index f520ed49..c3c6c4b2 100644
--- a/modules/core/Filters.js
+++ b/modules/core/Filters.js
@@ -17,7 +17,7 @@
/**
* @fileoverview Implements some useful macro filters.
*
- * To use this optional module, its repository needs to be added to the
+ * To use this optional module, its repository needs to be added to the
* application, for example by calling app.addRepository('modules/core/Filters.js')
*/
@@ -65,7 +65,7 @@ function titleize_filter(input) {
/**
- * Cuts a String at a certain position, and
+ * Cuts a String at a certain position, and
* optionally appends a suffix, if truncation
* has occurred.
*
@@ -118,7 +118,7 @@ function escapeXml_filter(input) {
* @see http://www.google.com/codesearch?q=escapeHtml
*/
function escapeHtml_filter(input) {
- var replace = Packages.org.mortbay.util.StringUtil.replace;
+ var replace = Packages.org.eclipse.jetty.util.StringUtil.replace;
var str = (input || "").toString();
return replace(replace(replace(replace(str, '&', '&'), '"', '"'), '>', '>'), '<', '<');
}
@@ -127,7 +127,7 @@ var h_filter = escapeHtml_filter;
/**
- * Escapes the characters in a String to be suitable
+ * Escapes the characters in a String to be suitable
* to use as an HTTP parameter value.
*
* @see http://www.google.com/codesearch?q=escapeUrl
@@ -145,7 +145,7 @@ function escapeUrl_filter(input, param, charset) {
* definitions.
*/
function escapeJavaScript_filter(input) {
- var replace = Packages.org.mortbay.util.StringUtil.replace;
+ var replace = Packages.org.eclipse.jetty.util.StringUtil.replace;
var str = (input || "").toString();
return replace(replace(replace(replace(replace(str, '"', '\\"'), "'", "\\'"), '\n', '\\n'), '\r', '\\r'), '\t', '\\t');
}
@@ -155,7 +155,7 @@ function escapeJavaScript_filter(input) {
* Replaces linebreaks with HTML linebreaks.
*/
function linebreakToHtml_filter(input) {
- var replace = Packages.org.mortbay.util.StringUtil.replace;
+ var replace = Packages.org.eclipse.jetty.util.StringUtil.replace;
var str = (input || "").toString();
return replace(str, '\n', '
');
}
@@ -171,7 +171,7 @@ function replace_filter(input, param, oldString, newString) {
var str = (input || "").toString();
var oldString = param["old"] != null ? param["old"] : oldString;
var newString = param["new"] != null ? param["new"] : newString;
- var replace = Packages.org.mortbay.util.StringUtil.replace;
+ var replace = Packages.org.eclipse.jetty.util.StringUtil.replace;
return replace(str, oldString, newString);
}
diff --git a/modules/core/JSON.js b/modules/core/JSON.js
index 5074b53f..56dfb991 100644
--- a/modules/core/JSON.js
+++ b/modules/core/JSON.js
@@ -1,179 +1,2 @@
-/*
- * Helma License Notice
- *
- * The contents of this file are subject to the Helma License
- * Version 2.0 (the "License"). You may not use this file except in
- * compliance with the License. A copy of the License is available at
- * http://adele.helma.org/download/helma/license.txt
- *
- * Copyright 1998-2006 Helma Software. All Rights Reserved.
- *
- * $RCSfile: JSON.js,v $
- * $Author$
- * $Revision$
- * $Date$
- */
-
-/**
- * @fileoverview Adds JSON methods to the Object, Array and String prototypes.
- *
- * To use this optional module, its repository needs to be added to the
- * application, for example by calling app.addRepository('modules/core/JSON.js')
- */
-
-/*
- json.js
- 2006-04-28 [http://www.json.org/json.js]
-
- This file adds these methods to JavaScript:
-
- object.toJSON()
-
- This method produces a JSON text from an object. The
- object must not contain any cyclical references.
-
- array.toJSON()
-
- This method produces a JSON text from an array. The
- array must not contain any cyclical references.
-
- string.parseJSON()
-
- This method parses a JSON text to produce an object or
- array. It will return false if there is an error.
-*/
-
-(function () {
- var m = {
- '\b': '\\b',
- '\t': '\\t',
- '\n': '\\n',
- '\f': '\\f',
- '\r': '\\r',
- '"' : '\\"',
- '\\': '\\\\'
- },
-
- s = {
- /**
- * @ignore
- */
- array: function (x) {
- var a = ['['], b, f, i, l = x.length, v;
- for (i = 0; i < l; i += 1) {
- v = x[i];
- f = s[typeof v];
- if (f) {
- v = f(v);
- if (typeof v == 'string') {
- if (b) {
- a[a.length] = ',';
- }
- a[a.length] = v;
- b = true;
- }
- }
- }
- a[a.length] = ']';
- return a.join('');
- },
-
- 'boolean': function (x) {
- return String(x);
- },
-
- 'null': function (x) {
- return "null";
- },
-
- /**
- * @ignore
- */
- number: function (x) {
- return isFinite(x) ? String(x) : 'null';
- },
-
- /**
- * @ignore
- */
- object: function (x) {
- if (x) {
- if (x instanceof Array) {
- return s.array(x);
- }
- var a = ['{'], b, f, i, v;
- for (i in x) {
- v = x[i];
- f = s[typeof v];
- if (f) {
- v = f(v);
- if (typeof v == 'string') {
- if (b) {
- a[a.length] = ',';
- }
- a.push(s.string(i), ':', v);
- b = true;
- }
- }
- }
- a[a.length] = '}';
- return a.join('');
- }
- return 'null';
- },
-
- /**
- * @ignore
- */
- string: function (x) {
- if (/["\\\x00-\x1f]/.test(x)) {
- x = x.replace(/([\x00-\x1f\\"])/g, function(a, b) {
- var c = m[b];
- if (c) {
- return c;
- }
- c = b.charCodeAt();
- return '\\u00' +
- Math.floor(c / 16).toString(16) +
- (c % 16).toString(16);
- });
- }
- return '"' + x + '"';
- }
- };
-
- /**
- * This method produces a JSON text from an object.
- * The object must not contain any cyclical references.
- */
- Object.prototype.toJSON = function () {
- return s.object(this);
- };
-
- /**
- * This method produces a JSON text from an array.
- * The array must not contain any cyclical references.
- */
- Array.prototype.toJSON = function () {
- return s.array(this);
- };
-
- Object.prototype.dontEnum("toJSON");
- Array.prototype.dontEnum("toJSON");
- return;
-})();
-
-
-/**
- * This method parses a JSON text to produce an object or
- * array. It will return false if there is an error.
- */
-String.prototype.parseJSON = function () {
- try {
- return !(/[^,:{}\[\]0-9.\-+Eaeflnr-u \n\r\t]/.test(this.replace(/"(\\.|[^"\\])*"/g, ''))) && eval('(' + this + ')');
- } catch (e) {
- return false;
- }
-};
-
-String.prototype.dontEnum("parseJSON");
+// This file intentionally left blank to prevent legacy code from
+// breaking when trying to include the obsolete JSON module.
diff --git a/modules/core/Object.js b/modules/core/Object.js
index 9cd756a1..41d59477 100644
--- a/modules/core/Object.js
+++ b/modules/core/Object.js
@@ -17,7 +17,7 @@
/**
* @fileoverview Adds useful methods to the JavaScript Object type.
*
- * To use this optional module, its repository needs to be added to the
+ * To use this optional module, its repository needs to be added to the
* application, for example by calling app.addRepository('modules/core/Object.js')
*/
@@ -30,42 +30,43 @@
*/
Object.prototype.clone = function(clone, recursive) {
- var getValue = function(value, recursive) {
- if ((value == null || typeof(value) !== "object") || recursive !== true) {
- return value;
- }
- return value.clone(null, recursive);
- };
+ var getValue = function(value, recursive) {
+ if (recursive !== true || value == null
+ || (typeof (value) !== "object" && typeof (value) !== "function")) {
+ return value;
+ }
+ return value.clone(null, recursive);
+ };
- if (typeof(this) === "object") {
- switch (this.constructor) {
- case Array:
- return this.map(function(value) {
- return getValue(value, recursive);
- });
+ if (typeof (this) === "object") {
+ if (this === null) {
+ return null;
+ }
+ switch (this.constructor) {
+ case String:
+ case Number:
+ case Boolean:
+ case Date:
+ return new this.constructor(this.valueOf());
- case null: // e.g. macro parameter objects
- if (clone == null) {
- clone = {};
- }
- // continue below
- case Object:
- case HopObject:
- if (clone == null) {
- clone = new this.constructor();
- }
- for (var propName in this) {
- clone[propName] = getValue(this[propName], recursive);
- }
- return clone;
+ case Array:
+ return this.map(function(value) {
+ return getValue(value, recursive);
+ });
- default:
- return new this.constructor(this.valueOf());
- }
- } else if (typeof(this) === "function" && this.constructor === RegExp) {
- return new RegExp(this.valueOf());
- }
- return this;
+ default:
+ if (clone == null) {
+ clone = new this.constructor();
+ }
+ for ( var propName in this) {
+ clone[propName] = getValue(this[propName], recursive);
+ }
+ return clone;
+ }
+ } else if (typeof (this) === "function" && this.constructor === RegExp) {
+ return new RegExp(this.valueOf());
+ }
+ return this;
};
@@ -78,11 +79,10 @@ Object.prototype.clone = function(clone, recursive) {
Object.prototype.reduce = function(recursive) {
var result = {};
for (var i in this) {
- if (this[i] instanceof HopObject == false) {
+ if (this[i] instanceof HopObject == false)
result[i] = this[i];
- } else if (recursive) {
+ else if (recursive)
result[i] = this.reduce(true);
- }
}
return result;
};
diff --git a/modules/core/all.js b/modules/core/all.js
index d31da393..78dcf793 100644
--- a/modules/core/all.js
+++ b/modules/core/all.js
@@ -14,7 +14,7 @@
* $Date$
*/
-// convenience SingleFileRepository to load all the
+// convenience SingleFileRepository to load all the
// Javascript library files in ./modules/core
app.addRepository('modules/core/Array.js');
@@ -24,5 +24,4 @@ app.addRepository('modules/core/Object.js');
app.addRepository('modules/core/String.js');
app.addRepository('modules/core/HopObject.js');
app.addRepository('modules/core/Global.js');
-app.addRepository('modules/core/JSON.js');
app.addRepository('modules/core/Filters.js');
diff --git a/modules/helma/Html.js b/modules/helma/Html.js
index 8cfab0d4..e70f2af7 100644
--- a/modules/helma/Html.js
+++ b/modules/helma/Html.js
@@ -477,7 +477,13 @@ helma.Html.prototype.dropDown = function(param, options, selectedValue, firstOpt
this.closeTag("option");
res.write("\n ");
}
+ var hasOpenGroup = false;
for (var i in options) {
+ if (options[i].group) {
+ hasOpenGroup && html.closeTag("optgroup");
+ html.openTag("optgroup", {label: options[i].group});
+ hasOpenGroup = true;
+ }
var attr = new Object();
var display = "";
if ((options[i] instanceof Array) && options[i].length > 0) {
@@ -503,6 +509,7 @@ helma.Html.prototype.dropDown = function(param, options, selectedValue, firstOpt
this.closeTag("option");
res.write("\n ");
}
+ hasOpenGroup && html.closeTag("optgroup");
this.closeTag("select");
res.write("\n ");
return;
diff --git a/modules/helma/Http.js b/modules/helma/Http.js
index 628ae100..b2932a5d 100644
--- a/modules/helma/Http.js
+++ b/modules/helma/Http.js
@@ -61,7 +61,9 @@ helma.Http = function() {
var responseHandler = function(connection, result) {
var input;
try {
- input = new java.io.BufferedInputStream(connection.getInputStream());
+ if (method !== 'DELETE') {
+ input = new java.io.BufferedInputStream(connection.getInputStream());
+ }
} catch (error) {
input = new java.io.BufferedInputStream(connection.getErrorStream());
}
diff --git a/modules/lib3k b/modules/lib3k
new file mode 120000
index 00000000..95e584a2
--- /dev/null
+++ b/modules/lib3k
@@ -0,0 +1 @@
+/Users/tobi/Projects/helma/modules/lib3k
\ No newline at end of file