dom/bindings/parser/tests/test_interface.py

Thu, 22 Jan 2015 13:21:57 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Thu, 22 Jan 2015 13:21:57 +0100
branch
TOR_BUG_9701
changeset 15
b8a032363ba2
permissions
-rw-r--r--

Incorporate requested changes from Mozilla in review:
https://bugzilla.mozilla.org/show_bug.cgi?id=1123480#c6

michael@0 1 import WebIDL
michael@0 2
michael@0 3 def WebIDLTest(parser, harness):
michael@0 4 parser.parse("interface Foo { };")
michael@0 5 results = parser.finish()
michael@0 6 harness.ok(True, "Empty interface parsed without error.")
michael@0 7 harness.check(len(results), 1, "Should be one production")
michael@0 8 harness.ok(isinstance(results[0], WebIDL.IDLInterface),
michael@0 9 "Should be an IDLInterface")
michael@0 10 iface = results[0]
michael@0 11 harness.check(iface.identifier.QName(), "::Foo", "Interface has the right QName")
michael@0 12 harness.check(iface.identifier.name, "Foo", "Interface has the right name")
michael@0 13 harness.check(iface.parent, None, "Interface has no parent")
michael@0 14
michael@0 15 parser.parse("interface Bar : Foo { };")
michael@0 16 results = parser.finish()
michael@0 17 harness.ok(True, "Empty interface parsed without error.")
michael@0 18 harness.check(len(results), 2, "Should be two productions")
michael@0 19 harness.ok(isinstance(results[1], WebIDL.IDLInterface),
michael@0 20 "Should be an IDLInterface")
michael@0 21 iface = results[1]
michael@0 22 harness.check(iface.identifier.QName(), "::Bar", "Interface has the right QName")
michael@0 23 harness.check(iface.identifier.name, "Bar", "Interface has the right name")
michael@0 24 harness.ok(isinstance(iface.parent, WebIDL.IDLInterface),
michael@0 25 "Interface has a parent")
michael@0 26
michael@0 27 parser = parser.reset()
michael@0 28 parser.parse("""
michael@0 29 interface QNameBase {
michael@0 30 attribute long foo;
michael@0 31 };
michael@0 32
michael@0 33 interface QNameDerived : QNameBase {
michael@0 34 attribute long long foo;
michael@0 35 attribute byte bar;
michael@0 36 };
michael@0 37 """)
michael@0 38 results = parser.finish()
michael@0 39 harness.check(len(results), 2, "Should be two productions")
michael@0 40 harness.ok(isinstance(results[0], WebIDL.IDLInterface),
michael@0 41 "Should be an IDLInterface")
michael@0 42 harness.ok(isinstance(results[1], WebIDL.IDLInterface),
michael@0 43 "Should be an IDLInterface")
michael@0 44 harness.check(results[1].parent, results[0], "Inheritance chain is right")
michael@0 45 harness.check(len(results[0].members), 1, "Expect 1 productions")
michael@0 46 harness.check(len(results[1].members), 2, "Expect 2 productions")
michael@0 47 base = results[0]
michael@0 48 derived = results[1]
michael@0 49 harness.check(base.members[0].identifier.QName(), "::QNameBase::foo",
michael@0 50 "Member has the right QName")
michael@0 51 harness.check(derived.members[0].identifier.QName(), "::QNameDerived::foo",
michael@0 52 "Member has the right QName")
michael@0 53 harness.check(derived.members[1].identifier.QName(), "::QNameDerived::bar",
michael@0 54 "Member has the right QName")
michael@0 55
michael@0 56 parser = parser.reset()
michael@0 57 threw = False
michael@0 58 try:
michael@0 59 parser.parse("""
michael@0 60 interface A : B {};
michael@0 61 interface B : A {};
michael@0 62 """)
michael@0 63 results = parser.finish()
michael@0 64 except:
michael@0 65 threw = True
michael@0 66
michael@0 67 harness.ok(threw, "Should not allow cycles in interface inheritance chains")
michael@0 68
michael@0 69 parser = parser.reset()
michael@0 70 threw = False
michael@0 71 try:
michael@0 72 parser.parse("""
michael@0 73 interface A : C {};
michael@0 74 interface C : B {};
michael@0 75 interface B : A {};
michael@0 76 """)
michael@0 77 results = parser.finish()
michael@0 78 except:
michael@0 79 threw = True
michael@0 80
michael@0 81 harness.ok(threw, "Should not allow indirect cycles in interface inheritance chains")
michael@0 82
michael@0 83 parser = parser.reset()
michael@0 84 threw = False
michael@0 85 try:
michael@0 86 parser.parse("""
michael@0 87 interface A {};
michael@0 88 interface B {};
michael@0 89 A implements B;
michael@0 90 B implements A;
michael@0 91 """)
michael@0 92 results = parser.finish()
michael@0 93 except:
michael@0 94 threw = True
michael@0 95
michael@0 96 harness.ok(threw, "Should not allow cycles via implements")
michael@0 97
michael@0 98 parser = parser.reset()
michael@0 99 threw = False
michael@0 100 try:
michael@0 101 parser.parse("""
michael@0 102 interface A {};
michael@0 103 interface C {};
michael@0 104 interface B {};
michael@0 105 A implements C;
michael@0 106 C implements B;
michael@0 107 B implements A;
michael@0 108 """)
michael@0 109 results = parser.finish()
michael@0 110 except:
michael@0 111 threw = True
michael@0 112
michael@0 113 harness.ok(threw, "Should not allow indirect cycles via implements")
michael@0 114
michael@0 115 parser = parser.reset()
michael@0 116 threw = False
michael@0 117 try:
michael@0 118 parser.parse("""
michael@0 119 interface A : B {};
michael@0 120 interface B {};
michael@0 121 B implements A;
michael@0 122 """)
michael@0 123 results = parser.finish()
michael@0 124 except:
michael@0 125 threw = True
michael@0 126
michael@0 127 harness.ok(threw, "Should not allow inheriting from an interface that implements us")
michael@0 128
michael@0 129 parser = parser.reset()
michael@0 130 threw = False
michael@0 131 try:
michael@0 132 parser.parse("""
michael@0 133 interface A : B {};
michael@0 134 interface B {};
michael@0 135 interface C {};
michael@0 136 B implements C;
michael@0 137 C implements A;
michael@0 138 """)
michael@0 139 results = parser.finish()
michael@0 140 except:
michael@0 141 threw = True
michael@0 142
michael@0 143 harness.ok(threw, "Should not allow inheriting from an interface that indirectly implements us")
michael@0 144
michael@0 145 parser = parser.reset()
michael@0 146 threw = False
michael@0 147 try:
michael@0 148 parser.parse("""
michael@0 149 interface A : B {};
michael@0 150 interface B : C {};
michael@0 151 interface C {};
michael@0 152 C implements A;
michael@0 153 """)
michael@0 154 results = parser.finish()
michael@0 155 except:
michael@0 156 threw = True
michael@0 157
michael@0 158 harness.ok(threw, "Should not allow indirectly inheriting from an interface that implements us")
michael@0 159
michael@0 160 parser = parser.reset()
michael@0 161 threw = False
michael@0 162 try:
michael@0 163 parser.parse("""
michael@0 164 interface A : B {};
michael@0 165 interface B : C {};
michael@0 166 interface C {};
michael@0 167 interface D {};
michael@0 168 C implements D;
michael@0 169 D implements A;
michael@0 170 """)
michael@0 171 results = parser.finish()
michael@0 172 except:
michael@0 173 threw = True
michael@0 174
michael@0 175 harness.ok(threw, "Should not allow indirectly inheriting from an interface that indirectly implements us")
michael@0 176
michael@0 177 parser = parser.reset()
michael@0 178 threw = False
michael@0 179 try:
michael@0 180 parser.parse("""
michael@0 181 interface A;
michael@0 182 interface B : A {};
michael@0 183 """)
michael@0 184 results = parser.finish()
michael@0 185 except:
michael@0 186 threw = True
michael@0 187
michael@0 188 harness.ok(threw, "Should not allow inheriting from an interface that is only forward declared")
michael@0 189
michael@0 190 parser = parser.reset()
michael@0 191 parser.parse("""
michael@0 192 [Constructor(long arg)]
michael@0 193 interface A {
michael@0 194 readonly attribute boolean x;
michael@0 195 void foo();
michael@0 196 };
michael@0 197 [Constructor]
michael@0 198 partial interface A {
michael@0 199 readonly attribute boolean y;
michael@0 200 void foo(long arg);
michael@0 201 };
michael@0 202 """);
michael@0 203 results = parser.finish();
michael@0 204 harness.check(len(results), 1,
michael@0 205 "Should have one result with partial interface")
michael@0 206 iface = results[0]
michael@0 207 harness.check(len(iface.members), 3,
michael@0 208 "Should have three members with partial interface")
michael@0 209 harness.check(iface.members[0].identifier.name, "x",
michael@0 210 "First member should be x with partial interface")
michael@0 211 harness.check(iface.members[1].identifier.name, "foo",
michael@0 212 "Second member should be foo with partial interface")
michael@0 213 harness.check(len(iface.members[1].signatures()), 2,
michael@0 214 "Should have two foo signatures with partial interface")
michael@0 215 harness.check(iface.members[2].identifier.name, "y",
michael@0 216 "Third member should be y with partial interface")
michael@0 217 harness.check(len(iface.ctor().signatures()), 2,
michael@0 218 "Should have two constructors with partial interface")
michael@0 219
michael@0 220 parser = parser.reset()
michael@0 221 parser.parse("""
michael@0 222 [Constructor]
michael@0 223 partial interface A {
michael@0 224 readonly attribute boolean y;
michael@0 225 void foo(long arg);
michael@0 226 };
michael@0 227 [Constructor(long arg)]
michael@0 228 interface A {
michael@0 229 readonly attribute boolean x;
michael@0 230 void foo();
michael@0 231 };
michael@0 232 """);
michael@0 233 results = parser.finish();
michael@0 234 harness.check(len(results), 1,
michael@0 235 "Should have one result with reversed partial interface")
michael@0 236 iface = results[0]
michael@0 237 harness.check(len(iface.members), 3,
michael@0 238 "Should have three members with reversed partial interface")
michael@0 239 harness.check(iface.members[0].identifier.name, "x",
michael@0 240 "First member should be x with reversed partial interface")
michael@0 241 harness.check(iface.members[1].identifier.name, "foo",
michael@0 242 "Second member should be foo with reversed partial interface")
michael@0 243 harness.check(len(iface.members[1].signatures()), 2,
michael@0 244 "Should have two foo signatures with reversed partial interface")
michael@0 245 harness.check(iface.members[2].identifier.name, "y",
michael@0 246 "Third member should be y with reversed partial interface")
michael@0 247 harness.check(len(iface.ctor().signatures()), 2,
michael@0 248 "Should have two constructors with reversed partial interface")
michael@0 249
michael@0 250 parser = parser.reset()
michael@0 251 threw = False
michael@0 252 try:
michael@0 253 parser.parse("""
michael@0 254 interface A {
michael@0 255 readonly attribute boolean x;
michael@0 256 };
michael@0 257 interface A {
michael@0 258 readonly attribute boolean y;
michael@0 259 };
michael@0 260 """)
michael@0 261 results = parser.finish()
michael@0 262 except:
michael@0 263 threw = True
michael@0 264 harness.ok(threw,
michael@0 265 "Should not allow two non-partial interfaces with the same name")
michael@0 266
michael@0 267 parser = parser.reset()
michael@0 268 threw = False
michael@0 269 try:
michael@0 270 parser.parse("""
michael@0 271 partial interface A {
michael@0 272 readonly attribute boolean x;
michael@0 273 };
michael@0 274 partial interface A {
michael@0 275 readonly attribute boolean y;
michael@0 276 };
michael@0 277 """)
michael@0 278 results = parser.finish()
michael@0 279 except:
michael@0 280 threw = True
michael@0 281 harness.ok(threw,
michael@0 282 "Must have a non-partial interface for a given name")
michael@0 283
michael@0 284 parser = parser.reset()
michael@0 285 threw = False
michael@0 286 try:
michael@0 287 parser.parse("""
michael@0 288 dictionary A {
michael@0 289 boolean x;
michael@0 290 };
michael@0 291 partial interface A {
michael@0 292 readonly attribute boolean y;
michael@0 293 };
michael@0 294 """)
michael@0 295 results = parser.finish()
michael@0 296 except:
michael@0 297 threw = True
michael@0 298 harness.ok(threw,
michael@0 299 "Should not allow a name collision between partial interface "
michael@0 300 "and other object")
michael@0 301
michael@0 302 parser = parser.reset()
michael@0 303 threw = False
michael@0 304 try:
michael@0 305 parser.parse("""
michael@0 306 dictionary A {
michael@0 307 boolean x;
michael@0 308 };
michael@0 309 interface A {
michael@0 310 readonly attribute boolean y;
michael@0 311 };
michael@0 312 """)
michael@0 313 results = parser.finish()
michael@0 314 except:
michael@0 315 threw = True
michael@0 316 harness.ok(threw,
michael@0 317 "Should not allow a name collision between interface "
michael@0 318 "and other object")
michael@0 319
michael@0 320 parser = parser.reset()
michael@0 321 threw = False
michael@0 322 try:
michael@0 323 parser.parse("""
michael@0 324 dictionary A {
michael@0 325 boolean x;
michael@0 326 };
michael@0 327 interface A;
michael@0 328 """)
michael@0 329 results = parser.finish()
michael@0 330 except:
michael@0 331 threw = True
michael@0 332 harness.ok(threw,
michael@0 333 "Should not allow a name collision between external interface "
michael@0 334 "and other object")
michael@0 335
michael@0 336 parser = parser.reset()
michael@0 337 threw = False
michael@0 338 try:
michael@0 339 parser.parse("""
michael@0 340 interface A {
michael@0 341 readonly attribute boolean x;
michael@0 342 };
michael@0 343 interface A;
michael@0 344 """)
michael@0 345 results = parser.finish()
michael@0 346 except:
michael@0 347 threw = True
michael@0 348 harness.ok(threw,
michael@0 349 "Should not allow a name collision between external interface "
michael@0 350 "and interface")
michael@0 351
michael@0 352 parser = parser.reset()
michael@0 353 parser.parse("""
michael@0 354 interface A;
michael@0 355 interface A;
michael@0 356 """)
michael@0 357 results = parser.finish()
michael@0 358 harness.ok(len(results) == 1 and
michael@0 359 isinstance(results[0], WebIDL.IDLExternalInterface),
michael@0 360 "Should allow name collisions between external interface "
michael@0 361 "declarations")
michael@0 362
michael@0 363 parser = parser.reset()
michael@0 364 threw = False
michael@0 365 try:
michael@0 366 parser.parse("""
michael@0 367 [SomeRandomAnnotation]
michael@0 368 interface A {
michael@0 369 readonly attribute boolean y;
michael@0 370 };
michael@0 371 """)
michael@0 372 results = parser.finish()
michael@0 373 except:
michael@0 374 threw = True
michael@0 375 harness.ok(threw,
michael@0 376 "Should not allow unknown extended attributes on interfaces")
michael@0 377
michael@0 378 parser = parser.reset()
michael@0 379 threw = False
michael@0 380 try:
michael@0 381 parser.parse("""
michael@0 382 interface B {};
michael@0 383 [ArrayClass]
michael@0 384 interface A : B {
michael@0 385 };
michael@0 386 """)
michael@0 387 results = parser.finish()
michael@0 388 except:
michael@0 389 threw = True
michael@0 390 harness.ok(threw,
michael@0 391 "Should not allow [ArrayClass] on interfaces with parents")
michael@0 392
michael@0 393 parser = parser.reset()
michael@0 394 threw = False
michael@0 395 try:
michael@0 396 parser.parse("""
michael@0 397 [ArrayClass]
michael@0 398 interface A {
michael@0 399 };
michael@0 400 """)
michael@0 401 results = parser.finish()
michael@0 402 except:
michael@0 403 threw = True
michael@0 404 harness.ok(not threw,
michael@0 405 "Should allow [ArrayClass] on interfaces without parents")

mercurial