Zmienne globalne deklarowane w javascript

Jak wszyscy wiemy nasz ulubiony język wzbogacił się o obsługę skryptów. W pakiecie od Sun dostajemy opakowany w standardowe API Rhino, czyli interpreter javascript rozwijany przez Mozilla Foundation.
Przeglądając dokumentację lub faq na stronie projektu Rhino poznamy podstawowe przypadki użycia. Dowiemy się jak wywołać skrypty i funkcje skryptowe, jak deklarować dla nich zmienne a także jak określić ich widoczność (scope). Bez problemu zadeklarujemy, korzystając z interfejsu ScriptContext, zmienne globalne. To po stronie aplikacji w javie.
Co jednak należy zrobić jeśli chcemy deklarować zmienne globalne w naszym skrypcie?

Najbardziej oczywista próba:

var sublek=0; //try to declare global variable
function createResponse()
{
        ++sublek;
	java.lang.System.out.println("sublek:"+ sublek);
	return sublek;
}

po prostym wywołaniu w pętli przyniesie odpowiedź negatywną. Zadeklarowana zmienna sublek jest lokalna dla skryptu. Kolejne wywołanie funkcji zwróci tą samą wartość.
Spróbujmy dostać się do kontekstu. Okazuje się że możemy użyć zmiennej context w samym skrypcie.
Należy użyć metod odpowiednio setAttribute() i getAttribute(). Teraz skrypt będzie wyglądać tak:

function createResponse()
{
	var sublek=0;
	//for first time we get null, after incrementation it will change to 1.0 
	sublek=context.getAttribute("sublek");
	java.lang.System.out.println("sublek:"+sublek);
 
	//this declares global variable   
	context.setAttribute("sublek",++sublek,context.GLOBAL_SCOPE);  
	return sublek;
}

No, chyba nie wygląda tak strasznie. Mała rzecz a może się przydać :) Jedynie o null trzeba zadbać - ale przecież potrafimy...
Aha, jeśli ktoś chce zobaczyć jak uruchamiałem skrypt to mniej więcej tak:

public class ASmallTestForScript
{    
    /** test script evaluator */
    private ScriptEngine _jsEngine;
    public ASmallTestForScript()
    {
        ScriptEngineManager manager=new ScriptEngineManager();
        _jsEngine = manager.getEngineByName("js");
    }
 
    public Object evalResponseFromScript() throws ScriptException, NoSuchMethodException,
            FileNotFoundException
    {
        _jsEngine.eval(getScriptReader());
        Object resp = ((Invocable) _jsEngine).invokeFunction("createResponse");
 
        return resp;
    }
 
    private Reader getScriptReader() throws ScriptException, NoSuchMethodException, FileNotFoundException
    {
        InputStream is = new FileInputStream("Tst.js");
        InputStreamReader reader=new InputStreamReader(is);
        return reader;
    }
 
    public static void main(String[] args) throws Exception
    {
        ASmallTestForScript s=new ASmallTestForScript();
        for(int i=0;i<10;i++)
        {
                Object resp=s.evalResponseFromScript();
                System.out.println(resp);
        }  
    }
}

Comments

Opcje przeglądania komentarzy

Wybierz preferowany sposób wyświetlania komentarzy i klinij na "Zapisz ustawienia", aby aktywować zmiany.

Rhino on Rails.

Cześć,

jak już przy Rhino jesteśmy to fajny filmik oglądnąłem przed kilkoma dniami.
Rhino on Rails

To poprostu to samo co Ruby on Rails, ale kod pisze się w Rhino, czyli w JavaScript. Jest to atrakcyjna alternatywa, dla ludzi którzy robią stronki HTML, CSS, i JavaScript i chcieliby pisać pełne aplikacje z dostępem do bazy danych, ale nie potrafią lub też nie chce im się uczyć PHP, Ruby, Perla, czy Javy.

Ciekawa uwaga autora odnośnie Ruby on Rails - RoR nie ma komponentów wizualnych jak JSF, Wicket czy GWT. Do tego prawdopodobnie skorzystają właśnie z Google Web Toolkit. Co ciekawe kod Webowy będzie też pisany w Rhino, ale będzie kompilowany przy pomocy takiego samego lub podobnego kompilatora jaki jest w GWT.

Jak widać Google chce osiągnąć przy pomocy konkretów to co Microsoft, próbuje zaprezentować w Microsoft Volta z wątpliwymi skutkami Is Volta's Javascript interop better than GWT?

Ciekaw jestem dalszego rozwoju wydarzeń na tej arenie.

Pozdrawiam,
Gabriel.