summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGravatar Artyom Shalkhakov <artyom.shalkhakov@gmail.com>2018-05-08 16:03:24 +0600
committerGravatar Artyom Shalkhakov <artyom.shalkhakov@gmail.com>2018-05-08 16:03:24 +0600
commitc293746d4c34ccb7abb8af41f7d05940aa7e4076 (patch)
tree052e8bf308ba2e2f8de626ec1426f9a3841728a3
parente1ae0ce918c234cbb0b5a6ee72e0443bd04d4127 (diff)
Adding Selenium-based checking to tests.
-rw-r--r--.gitignore5
-rw-r--r--tests/DynChannel.py20
-rw-r--r--tests/Makefile17
-rw-r--r--tests/alert.py11
-rw-r--r--tests/alert.ur2
-rw-r--r--tests/alert.urp3
-rw-r--r--tests/align.py11
-rw-r--r--tests/appjs.py11
-rw-r--r--tests/appjs.ur2
-rw-r--r--tests/ascdesc.py11
-rw-r--r--tests/ascdesc.ur14
-rw-r--r--tests/ascdesc.urp3
-rw-r--r--tests/attrMangle.py11
-rw-r--r--tests/attrs_escape.py10
-rw-r--r--tests/attrs_escape.ur10
-rw-r--r--tests/autocomp.py15
-rw-r--r--tests/autocomp.ur8
-rw-r--r--tests/base.py29
-rw-r--r--tests/bindpat.py9
-rw-r--r--tests/bindpat.ur7
-rwxr-xr-xtests/driver.sh25
-rw-r--r--tests/entities.py14
-rw-r--r--tests/entities.ur6
-rw-r--r--tests/fact.py10
-rw-r--r--tests/filter.py9
-rw-r--r--tests/filter.ur17
-rw-r--r--tests/jsonTest.py16
-rw-r--r--tests/jsonTest.ur4
28 files changed, 280 insertions, 30 deletions
diff --git a/.gitignore b/.gitignore
index b30fa842..377a9e5d 100644
--- a/.gitignore
+++ b/.gitignore
@@ -76,3 +76,8 @@ libtool
include/urweb/config.h
include/urweb/config.h.in
include/urweb/stamp-h1
+
+# python files
+# Byte-compiled / optimized / DLL files
+__pycache__/
+*.py[cod]
diff --git a/tests/DynChannel.py b/tests/DynChannel.py
new file mode 100644
index 00000000..7af5ea78
--- /dev/null
+++ b/tests/DynChannel.py
@@ -0,0 +1,20 @@
+import unittest
+import base
+
+class Suite(base.Base):
+ def test_1(self):
+ """Test case 1"""
+ self.start('DynChannel/main')
+
+ # initial state: only Register is visible
+ reg = self.xpath('button')
+ reg.click()
+ # and we get two another state: either Register or Send visible
+ send = self.xpath('span/button')
+ send.click()
+ alert = self.driver.switch_to.alert
+ self.assertEqual("Got something from the channel", alert.text)
+ alert.accept()
+ # we got the message back
+ span = self.xpath('span/span')
+ self.assertEqual("blabla", span.text)
diff --git a/tests/Makefile b/tests/Makefile
index 5313d12d..63ae555e 100644
--- a/tests/Makefile
+++ b/tests/Makefile
@@ -2,3 +2,20 @@ all: test.o
test.o: test.c
gcc -c test.c -o test.o
+###
+
+simple::
+ ./driver.sh alert
+ ./driver.sh align
+ ./driver.sh appjs
+ ./driver.sh ascdesc
+ echo ./driver.sh attrMangle
+ ./driver.sh attrs_escape
+ echo ./driver.sh attrs
+ ./driver.sh autocomp
+ ./driver.sh bindpat
+ ./driver.sh DynChannel
+ ./driver.sh jsonTest
+ ./driver.sh entities
+ ./driver.sh fact
+ ./driver.sh filter
diff --git a/tests/alert.py b/tests/alert.py
new file mode 100644
index 00000000..4b783d50
--- /dev/null
+++ b/tests/alert.py
@@ -0,0 +1,11 @@
+import unittest
+import base
+
+class Suite(base.Base):
+ def test_1(self):
+ """Test case 1"""
+ self.start()
+ el = self.xpath('a')
+ el.click()
+ alert = self.driver.switch_to.alert
+ self.assertEqual("You clicked it! That's some fancy shooting!", alert.text)
diff --git a/tests/alert.ur b/tests/alert.ur
index 3fe68d75..7a290921 100644
--- a/tests/alert.ur
+++ b/tests/alert.ur
@@ -1,3 +1,3 @@
fun main () : transaction page = return <xml><body>
- <a onclick={alert "You clicked it! That's some fancy shooting!"}>Click Me!</a>
+ <a onclick={fn _ => alert "You clicked it! That's some fancy shooting!"}>Click Me!</a>
</body></xml>
diff --git a/tests/alert.urp b/tests/alert.urp
deleted file mode 100644
index 3976e9b0..00000000
--- a/tests/alert.urp
+++ /dev/null
@@ -1,3 +0,0 @@
-debug
-
-alert
diff --git a/tests/align.py b/tests/align.py
new file mode 100644
index 00000000..525ab4e6
--- /dev/null
+++ b/tests/align.py
@@ -0,0 +1,11 @@
+import unittest
+import base
+
+class Suite(base.Base):
+ def test_1(self):
+ """Test case 1"""
+ self.start()
+ el = self.xpath('p[@align="left"]')
+ self.assertEqual("Left", el.text)
+ el = self.xpath('p[@align="right"]')
+ self.assertEqual("Right", el.text)
diff --git a/tests/appjs.py b/tests/appjs.py
new file mode 100644
index 00000000..02ac2193
--- /dev/null
+++ b/tests/appjs.py
@@ -0,0 +1,11 @@
+import unittest
+import base
+
+class Suite(base.Base):
+ def test_1(self):
+ """Test case 1"""
+ self.start()
+ el = self.xpath('button')
+ el.click()
+ alert = self.driver.switch_to.alert
+ self.assertEqual("3", alert.text)
diff --git a/tests/appjs.ur b/tests/appjs.ur
index 01e9f345..403b0b4e 100644
--- a/tests/appjs.ur
+++ b/tests/appjs.ur
@@ -1,5 +1,5 @@
fun id n = if n = 0 then 0 else 1 + id (n - 1)
fun main () : transaction page = return <xml><body>
- <button onclick={alert (show (id 3))}/>
+ <button onclick={fn _ => alert (show (id 3))}/>
</body></xml>
diff --git a/tests/ascdesc.py b/tests/ascdesc.py
new file mode 100644
index 00000000..6b514f4e
--- /dev/null
+++ b/tests/ascdesc.py
@@ -0,0 +1,11 @@
+import unittest
+import base
+
+class Suite(base.Base):
+ def test_1(self):
+ """Test case 1"""
+ self.start('Ascdesc/main')
+ el = self.xpath('p[1]')
+ self.assertEqual("1; 2; 3;", el.text)
+ el = self.xpath('p[2]')
+ self.assertEqual("3; 2; 1;", el.text)
diff --git a/tests/ascdesc.ur b/tests/ascdesc.ur
index 59dd0169..fadac27d 100644
--- a/tests/ascdesc.ur
+++ b/tests/ascdesc.ur
@@ -4,7 +4,15 @@ fun sortEm b =
queryX1 (SELECT * FROM t ORDER BY t.A {if b then sql_asc else sql_desc})
(fn r => <xml>{[r.A]}; </xml>)
-fun main () : transaction page = return <xml><body>
- <a link={sortEm True}>Ascending</a><br/>
- <a link={sortEm False}>Descending</a>
+task initialize = fn () =>
+ dml (INSERT INTO t (A) VALUES (1));
+ dml (INSERT INTO t (A) VALUES (2));
+ dml (INSERT INTO t (A) VALUES (3))
+
+fun main () : transaction page =
+ p1 <- sortEm True;
+ p2 <- sortEm False;
+ return <xml><body>
+ <p>{p1}</p>
+ <p>{p2}</p>
</body></xml>
diff --git a/tests/ascdesc.urp b/tests/ascdesc.urp
index 3e0b075d..a1c4124e 100644
--- a/tests/ascdesc.urp
+++ b/tests/ascdesc.urp
@@ -1,4 +1,3 @@
-database dbname=test
-sql ascdesc.sql
+database dbname=ascdesc
ascdesc \ No newline at end of file
diff --git a/tests/attrMangle.py b/tests/attrMangle.py
new file mode 100644
index 00000000..d3b24244
--- /dev/null
+++ b/tests/attrMangle.py
@@ -0,0 +1,11 @@
+import unittest
+import base
+
+class Suite(base.Base):
+ def test_1(self):
+ """Test case 1"""
+ self.start()
+ el = self.xpath('goofy[@name eq "beppo" and @data-role eq "excellence"]')
+ el.click()
+ alert = self.driver.switch_to.alert
+ self.assertEqual("You clicked it! That's some fancy shooting!", alert.text)
diff --git a/tests/attrs_escape.py b/tests/attrs_escape.py
new file mode 100644
index 00000000..fc9f91b5
--- /dev/null
+++ b/tests/attrs_escape.py
@@ -0,0 +1,10 @@
+import unittest
+import base
+
+class Suite(base.Base):
+ def test_1(self):
+ """Test case 1"""
+ self.start()
+ el = self.xpath('form/input')
+ val = el.get_attribute('value')
+ self.assertEqual("\"Well hey\"\nWow", val)
diff --git a/tests/attrs_escape.ur b/tests/attrs_escape.ur
index 12de101e..87d554fe 100644
--- a/tests/attrs_escape.ur
+++ b/tests/attrs_escape.ur
@@ -1,4 +1,6 @@
-val main = fn () => <html><body>
- <font face="\"Well hey\"
-Wow">Welcome</font>
-</body></html>
+fun main () : transaction page = return <xml><body>
+<form>
+ <submit value="\"Well hey\"
+Wow"/>
+</form>
+</body></xml>
diff --git a/tests/autocomp.py b/tests/autocomp.py
new file mode 100644
index 00000000..28c3b7d2
--- /dev/null
+++ b/tests/autocomp.py
@@ -0,0 +1,15 @@
+import unittest
+import base
+
+class Suite(base.Base):
+ def test_1(self):
+ """Test case 1"""
+ self.start()
+ txt = self.xpath('div')
+ self.assertEqual('/', txt.text)
+ inp = self.xpath('/input')
+ inp.send_keys('hello there')
+ self.assertEqual('hello there /', txt.text)
+ btn = self.xpath('button')
+ btn.click()
+ self.assertEqual("hello there / hello there", txt.text)
diff --git a/tests/autocomp.ur b/tests/autocomp.ur
index d4e6a287..753318f7 100644
--- a/tests/autocomp.ur
+++ b/tests/autocomp.ur
@@ -2,10 +2,10 @@ fun main () : transaction page =
a <- source "";
b <- source "";
return <xml><body>
- <form>
- <textbox{#A} source={a}/>
- <button onclick={x <- get a; set b x}/>
+ <ctextbox source={a}/>
+ <button onclick={fn _ => x <- get a; set b x}>click me</button>
+ <div>
<dyn signal={v <- signal a; return <xml>{[v]}</xml>}/>
/ <dyn signal={v <- signal b; return <xml>{[v]}</xml>}/>
- </form>
+ </div>
</body></xml>
diff --git a/tests/base.py b/tests/base.py
new file mode 100644
index 00000000..b9a026f2
--- /dev/null
+++ b/tests/base.py
@@ -0,0 +1,29 @@
+# use pip install selenium first
+# ensure you have both chome driver & chrome installed
+
+import unittest
+from selenium import webdriver
+from selenium.common.exceptions import NoSuchElementException
+
+class Base(unittest.TestCase):
+ """Include test cases on a given url"""
+
+ def start(self, path='main'):
+ self.driver.get('http://localhost:8080/' + path)
+ def xpath(self, path):
+ return self.driver.find_element_by_xpath('/html/body/'+path)
+ def body_text(self):
+ return self.driver.find_element_by_xpath('/html/body').text
+
+ def setUp(self):
+ """Start web driver"""
+ chrome_options = webdriver.ChromeOptions()
+ chrome_options.add_argument('--no-sandbox')
+ chrome_options.add_argument('--headless')
+ chrome_options.add_argument('--disable-gpu')
+ self.driver = webdriver.Chrome(options=chrome_options)
+ self.driver.implicitly_wait(10)
+
+ def tearDown(self):
+ """Stop web driver"""
+ self.driver.quit()
diff --git a/tests/bindpat.py b/tests/bindpat.py
new file mode 100644
index 00000000..6c33f52f
--- /dev/null
+++ b/tests/bindpat.py
@@ -0,0 +1,9 @@
+import unittest
+import base
+
+class Suite(base.Base):
+ def test_1(self):
+ """Test case 1"""
+ self.driver.get('http://localhost:8080/main')
+ el = self.driver.find_element_by_xpath('/html/body')
+ self.assertEqual("1, 2, hi, 2.34, 8, 9", el.text)
diff --git a/tests/bindpat.ur b/tests/bindpat.ur
index bca4bd41..8fd6eb39 100644
--- a/tests/bindpat.ur
+++ b/tests/bindpat.ur
@@ -1,6 +1,9 @@
fun main () : transaction page =
(a, b) <- return (1, 2);
{C = c, ...} <- return {C = "hi", D = False};
- d <- return 2.34;
- {1 = e, 2 = f} <- return (8, 9);
+ let
+ val d = 2.34
+ val {1 = e, 2 = f} = (8, 9)
+ in
return <xml>{[a]}, {[b]}, {[c]}, {[d]}, {[e]}, {[f]}</xml>
+ end \ No newline at end of file
diff --git a/tests/driver.sh b/tests/driver.sh
new file mode 100755
index 00000000..cc62644b
--- /dev/null
+++ b/tests/driver.sh
@@ -0,0 +1,25 @@
+#!/bin/bash
+
+if [[ $# -eq 0 ]] ; then
+ echo 'Supply at least one argument'
+ exit 1
+fi
+
+TESTDB=/tmp/$1.db
+TESTSQL=/tmp/$1.sql
+TESTPID=/tmp/$1.pid
+TESTSRV=./$1.exe
+
+rm -f $TESTDB $TESTSQL $TESTPID $TESTSRV
+../bin/urweb -debug -boot -noEmacs -dbms sqlite -db $TESTDB -sql $TESTSQL "$1" || exit 1
+
+if [ -e $TESTSQL ]
+then
+ sqlite3 $TESTDB < $TESTSQL
+fi
+
+$TESTSRV -q -a 127.0.0.1 &
+echo $! >> $TESTPID
+sleep 1
+python -m unittest $1.py
+kill `cat $TESTPID`
diff --git a/tests/entities.py b/tests/entities.py
new file mode 100644
index 00000000..d9087cbf
--- /dev/null
+++ b/tests/entities.py
@@ -0,0 +1,14 @@
+import unittest
+import base
+
+class Suite(base.Base):
+ def test_1(self):
+ """Test case 1"""
+ self.start()
+ p = self.xpath('p[1]')
+ self.assertEqual('Hello world! & so on, © me today (8 €)', p.text)
+ p = self.xpath('p[2]')
+ self.assertEqual('♠ ♣ ♥ ♦', p.text)
+ p = self.xpath('p[3]')
+ self.assertEqual('† DANGER †', p.text)
+
diff --git a/tests/entities.ur b/tests/entities.ur
index 8b78edbc..1f45520d 100644
--- a/tests/entities.ur
+++ b/tests/entities.ur
@@ -1,5 +1,5 @@
fun main () : transaction page = return <xml><body>
- Hello world! &amp; so on, &copy; me today (8 &euro;)<br/>
- &spades; &clubs; &hearts; &diams;<br/>
- &dagger; DANGER &dagger;
+ <p>Hello world! &amp; so on, &copy; me today (8 &euro;)</p>
+ <p>&spades; &clubs; &hearts; &diams;</p>
+ <p>&dagger; DANGER &dagger;</p>
</body></xml>
diff --git a/tests/fact.py b/tests/fact.py
new file mode 100644
index 00000000..3dcd6f71
--- /dev/null
+++ b/tests/fact.py
@@ -0,0 +1,10 @@
+import unittest
+import base
+
+class Suite(base.Base):
+ def test_1(self):
+ """Test case 1"""
+ self.start()
+ b = self.driver.find_element_by_xpath('/html/body')
+ self.assertEqual('3628800, 3628800', b.text)
+
diff --git a/tests/filter.py b/tests/filter.py
new file mode 100644
index 00000000..f68f8f88
--- /dev/null
+++ b/tests/filter.py
@@ -0,0 +1,9 @@
+import unittest
+import base
+
+class Suite(base.Base):
+ def test_1(self):
+ """Test case 1"""
+ self.start('Filter/main')
+ tx = self.body_text()
+ self.assertEqual("4, 4; 44, 4.4;", tx)
diff --git a/tests/filter.ur b/tests/filter.ur
index efd326c3..2691a939 100644
--- a/tests/filter.ur
+++ b/tests/filter.ur
@@ -1,9 +1,16 @@
-fun filter [fs ::: {Type}] [ks] (t : sql_table fs ks) (p : sql_exp [T = fs] [] [] bool)
- : sql_query [T = fs] [] =
+fun filter [fs ::: {Type}] [ks] (t : sql_table fs ks) (p : sql_exp [T = fs] [] [] bool) =
(SELECT * FROM t WHERE {p})
table t : { A : int, B : float }
-fun main () =
- queryX (filter t (WHERE t.A > 3))
- (fn r => <xml>{[r.T.A]}, {[r.T.B]}</xml>)
+task initialize = fn () =>
+ dml (INSERT INTO t (A, B) VALUES (1, 2.0));
+ dml (INSERT INTO t (A, B) VALUES (2, 1.0));
+ dml (INSERT INTO t (A, B) VALUES (3, 3.0));
+ dml (INSERT INTO t (A, B) VALUES (4, 4.0));
+ dml (INSERT INTO t (A, B) VALUES (44, 4.4))
+
+fun main () : transaction page =
+ r <- queryX (filter t (WHERE t.A > 3))
+ (fn r => <xml>{[r.T.A]}, {[r.T.B]}; </xml>);
+ return <xml><body>{r}</body></xml>
diff --git a/tests/jsonTest.py b/tests/jsonTest.py
new file mode 100644
index 00000000..d9147511
--- /dev/null
+++ b/tests/jsonTest.py
@@ -0,0 +1,16 @@
+import unittest
+import base
+
+class Suite(base.Base):
+ def test_1(self):
+ """Test case 1"""
+ self.start()
+
+ pre = self.xpath('pre[1]')
+ self.assertEqual('line 1\nline 2', pre.text)
+
+ pre = self.xpath('pre[2]')
+ self.assertEqual('1 :: 2 :: 3 :: []', pre.text)
+
+ pre = self.xpath('pre[3]')
+ self.assertEqual('["hi","bye\\"","hehe"]', pre.text)
diff --git a/tests/jsonTest.ur b/tests/jsonTest.ur
index 1be6e7b5..38d0d201 100644
--- a/tests/jsonTest.ur
+++ b/tests/jsonTest.ur
@@ -2,6 +2,6 @@ open Json
fun main () : transaction page = return <xml><body>
<pre>{[ fromJson "\"line 1\\nline 2\"" : string ]}</pre><br/>
- {[fromJson "[1, 2, 3]" : list int]}<br/>
- {[toJson ("hi" :: "bye\"" :: "hehe" :: [])]}
+ <pre>{[fromJson "[1, 2, 3]" : list int]}</pre><br/>
+ <pre>{[toJson ("hi" :: "bye\"" :: "hehe" :: [])]}</pre>
</body></xml>