summaryrefslogtreecommitdiffstats
path: root/testing/web-platform/tests/IndexedDB/key_invalid.htm
blob: cf649b07d0572cb6543f7ea081ac8db9b0a95e58 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
<!DOCTYPE html>
<!-- Submitted from TestTWF Paris -->
<meta charset=utf-8">
<title>Invalid key</title>
<link rel=help href="http://dvcs.w3.org/hg/IndexedDB/raw-file/tip/Overview.html#key-construct">
<link rel=assert title="A value is said to be a valid key if it is one of the following types: Array JavaScript objects [ECMA-262], DOMString [WEBIDL], Date [ECMA-262] or float [WEBIDL]. However Arrays are only valid keys if every item in the array is defined and is a valid key (i.e. sparse arrays can not be valid keys) and if the Array doesn't directly or indirectly contain itself. Any non-numeric properties are ignored, and thus does not affect whether the Array is a valid key. Additionally, if the value is of type float, it is only a valid key if it is not NaN, and if the value is of type Date it is only a valid key if its [[PrimitiveValue]] internal property, as defined by [ECMA-262], is not NaN. Conforming user agents must support all valid keys as keys.">
<!-- original author -->
<link rel=author href="mailto:odinho@opera.com" title="Odin Hørthe Omdal">
<!-- some additions by Baptiste Fontaine (batifon@yahoo.fr) -->
<script src=/resources/testharness.js></script>
<script src=/resources/testharnessreport.js></script>
<script src=resources/support.js></script>

<script>
    var db        = createdb_for_multiple_tests(),
        // cache for ObjectStores
        objStore  = null,
        objStore2 = null;

    function is_cloneable(o) {
        try {
            self.postMessage(o, '*');
            return true;
        } catch (ex) {
            return false;
        }
    }

    function invalid_key(desc, key) {
        var t = async_test(document.title + " - " + desc);

        // set the current test, and run it
        db.setTest(t).onupgradeneeded = function(e) {
            objStore = objStore || e.target.result.createObjectStore("store");
            assert_throws_dom('DataError', function() {
                objStore.add("value", key);
            });

            if (is_cloneable(key)) {
                objStore2 = objStore2 || e.target.result.createObjectStore("store2", { keyPath: ["x", "keypath"] });
                assert_throws_dom('DataError', function() {
                    objStore2.add({ x: "value", keypath: key });
                });
            }
            this.done();
        };
    }

    var fake_array = {
        length      : 0,
        constructor : Array
    };

    var ArrayClone = function(){};
    ArrayClone.prototype = Array;
    var ArrayClone_instance = new ArrayClone();

    // booleans
    invalid_key( 'true'  , true );
    invalid_key( 'false' , false );

    // null/NaN/undefined
    invalid_key( 'null'      , null );
    invalid_key( 'NaN'       , NaN );
    invalid_key( 'undefined' , undefined );
    invalid_key( 'undefined2');

    // functions
    invalid_key( 'function() {}', function(){} );

    // objects
    invalid_key( '{}'                           , {} );
    invalid_key( '{ obj: 1 }'                   , { obj: 1 });
    invalid_key( 'Math'                         , Math );
    invalid_key( 'window'                       , window );
    invalid_key( '{length:0,constructor:Array}' , fake_array );
    invalid_key( 'Array clone’s instance'       , ArrayClone_instance );
    invalid_key( 'Array (object)'               , Array );
    invalid_key( 'String (object)'              , String );
    invalid_key( 'new String()'                 , new String() );
    invalid_key( 'new Number()'                 , new Number() );
    invalid_key( 'new Boolean()'                , new Boolean() );

    // arrays
    invalid_key( '[{}]'                     , [{}] );
    invalid_key( '[[], [], [], [[ Date ]]]' , [ [], [], [], [[ Date ]] ] );
    invalid_key( '[undefined]'              , [undefined] );
    invalid_key( '[,1]'                     , [,1] );

    invalid_key( 'document.getElements'
                +'ByTagName("script")'      , document.getElementsByTagName("script") );

    //  dates
    invalid_key( 'new Date(NaN)'      , new Date(NaN) );
    invalid_key( 'new Date(Infinity)' , new Date(Infinity) );

    // regexes
    invalid_key( '/foo/'        , /foo/ );
    invalid_key( 'new RegExp()' , new RegExp() );

    var sparse = [];
    sparse[10] = "hei";
    invalid_key('sparse array', sparse);

    var sparse2 = [];
    sparse2[0]  = 1;
    sparse2[""] = 2;
    sparse2[2]  = 3;
    invalid_key('sparse array 2', sparse2);

    invalid_key('[[1], [3], [7], [[ sparse array ]]]', [ [1], [3], [7], [[ sparse2 ]] ]);

    // sparse3
    invalid_key( '[1,2,3,,]', [1,2,3,,] );

    var recursive = [];
    recursive.push(recursive);
    invalid_key('array directly contains self', recursive);

    var recursive2 = [];
    recursive2.push([recursive2]);
    invalid_key('array indirectly contains self', recursive2);

    var recursive3 = [recursive];
    invalid_key('array member contains self', recursive3);

    invalid_key('proxy of an array', new Proxy([1,2,3], {}));

</script>

<div id=log></div>