1<p align="center"> 2 <a href="https://travis-ci.org/evcohen/jsx-ast-utils"> 3 <img src="https://api.travis-ci.org/evcohen/jsx-ast-utils.svg?branch=master" 4 alt="build status"> 5 </a> 6 <a href="https://npmjs.org/package/jsx-ast-utils"> 7 <img src="https://img.shields.io/npm/v/jsx-ast-utils.svg" 8 alt="npm version"> 9 </a> 10 <a href="https://github.com/evcohen/jsx-ast-utils/blob/master/LICENSE.md"> 11 <img src="https://img.shields.io/npm/l/jsx-ast-utils.svg" 12 alt="license"> 13 </a> 14 <a href='https://coveralls.io/github/evcohen/jsx-ast-utils?branch=master'> 15 <img src='https://coveralls.io/repos/github/evcohen/jsx-ast-utils/badge.svg?branch=master' alt='Coverage Status' /> 16 </a> 17 <a href='https://npmjs.org/package/jsx-ast-utils'> 18 <img src='https://img.shields.io/npm/dt/jsx-ast-utils.svg' 19 alt='Total npm downloads' /> 20 </a> 21</p> 22 23# jsx-ast-utils 24 25AST utility module for statically analyzing JSX. 26 27## Installation 28```sh 29$ npm i jsx-ast-utils --save 30``` 31 32## Usage 33This is a utility module to evaluate AST objects for JSX syntax. This can be super useful when writing linting rules for JSX code. It was originally in the code for [eslint-plugin-jsx-a11y](https://github.com/evcohen/eslint-plugin-jsx-a11y), however I thought it could be useful to be extracted and maintained separately so **you** could write new interesting rules to statically analyze JSX. 34 35### ESLint example 36```js 37import { hasProp } from 'jsx-ast-utils'; 38// OR: var hasProp = require('jsx-ast-utils').hasProp; 39// OR: const hasProp = require('jsx-ast-utils/hasProp'); 40// OR: import hasProp from 'jsx-ast-utils/hasProp'; 41 42module.exports = context => ({ 43 JSXOpeningElement: node => { 44 const onChange = hasProp(node.attributes, 'onChange'); 45 46 if (onChange) { 47 context.report({ 48 node, 49 message: `No onChange!` 50 }); 51 } 52 } 53}); 54``` 55 56## API 57### AST Resources 581. [JSX spec](https://github.com/facebook/jsx/blob/master/AST.md) 592. [JS spec](https://github.com/estree/estree/blob/master/spec.md) 60 61### hasProp 62```js 63hasProp(props, prop, options); 64``` 65Returns boolean indicating whether an prop exists as an attribute on a JSX element node. 66 67#### Props 68Object - The attributes on the visited node. (Usually `node.attributes`). 69#### Prop 70String - A string representation of the prop you want to check for existence. 71#### Options 72Object - An object representing options for existence checking 73 1. `ignoreCase` - automatically set to `true`. 74 2. `spreadStrict` - automatically set to `true`. This means if spread operator exists in 75 props, it will assume the prop you are looking for is not in the spread. 76 Example: `<div {...props} />` looking for specific prop here will return false if `spreadStrict` is `true`. 77 78<hr /> 79 80### hasAnyProp 81 82```js 83hasAnyProp(props, prop, options); 84``` 85Returns a boolean indicating if **any** of props in `prop` argument exist on the node. 86 87#### Props 88Object - The attributes on the visited node. (Usually `node.attributes`). 89#### Prop 90Array<String> - An array of strings representing the props you want to check for existence. 91#### Options 92Object - An object representing options for existence checking 93 1. `ignoreCase` - automatically set to `true`. 94 2. `spreadStrict` - automatically set to `true`. This means if spread operator exists in 95 props, it will assume the prop you are looking for is not in the spread. 96 Example: `<div {...props} />` looking for specific prop here will return false if `spreadStrict` is `true`. 97 98<hr /> 99 100### hasEveryProp 101 102```js 103hasEveryProp(props, prop, options); 104``` 105Returns a boolean indicating if **all** of props in `prop` argument exist on the node. 106 107#### Props 108Object - The attributes on the visited node. (Usually `node.attributes`). 109#### Prop 110Array<String> - An array of strings representing the props you want to check for existence. 111#### Options 112Object - An object representing options for existence checking 113 1. `ignoreCase` - automatically set to `true`. 114 2. `spreadStrict` - automatically set to `true`. This means if spread operator exists in 115 props, it will assume the prop you are looking for is not in the spread. 116 Example: `<div {...props} />` looking for specific prop here will return false if `spreadStrict` is `true`. 117 118<hr /> 119 120### getProp 121 122```js 123getProp(props, prop, options); 124``` 125Returns the JSXAttribute itself or undefined, indicating the prop is not present on the JSXOpeningElement. 126 127#### Props 128Object - The attributes on the visited node. (Usually `node.attributes`). 129#### Prop 130String - A string representation of the prop you want to check for existence. 131#### Options 132Object - An object representing options for existence checking 133 1. `ignoreCase` - automatically set to `true`. 134 135<hr /> 136 137### elementType 138```js 139elementType(node) 140``` 141Returns the tagName associated with a JSXElement. 142 143#### Node 144Object - The visited JSXElement node object. 145 146<hr /> 147 148### getPropValue 149 150```js 151getPropValue(prop); 152``` 153Returns the value of a given attribute. Different types of attributes have their associated values in different properties on the object. 154 155This function should return the most *closely* associated value with the intention of the JSX. 156 157#### Prop 158Object - The JSXAttribute collected by AST parser. 159 160<hr /> 161 162### getLiteralPropValue 163 164```js 165getLiteralPropValue(prop); 166``` 167Returns the value of a given attribute. Different types of attributes have their associated values in different properties on the object. 168 169This function should return a value only if we can extract a literal value from its attribute (i.e. values that have generic types in JavaScript - strings, numbers, booleans, etc.) 170 171#### Prop 172Object - The JSXAttribute collected by AST parser. 173 174<hr /> 175 176### propName 177 178```js 179propName(prop); 180``` 181Returns the name associated with a JSXAttribute. For example, given `<div foo="bar" />` and the JSXAttribute for `foo`, this will return the string `"foo"`. 182 183#### Prop 184Object - The JSXAttribute collected by AST parser. 185 186<hr /> 187 188### eventHandlers 189 190```js 191console.log(eventHandlers); 192/* 193[ 194 'onCopy', 195 'onCut', 196 'onPaste', 197 'onCompositionEnd', 198 'onCompositionStart', 199 'onCompositionUpdate', 200 'onKeyDown', 201 'onKeyPress', 202 'onKeyUp', 203 'onFocus', 204 'onBlur', 205 'onChange', 206 'onInput', 207 'onSubmit', 208 'onClick', 209 'onContextMenu', 210 'onDblClick', 211 'onDoubleClick', 212 'onDrag', 213 'onDragEnd', 214 'onDragEnter', 215 'onDragExit', 216 'onDragLeave', 217 'onDragOver', 218 'onDragStart', 219 'onDrop', 220 'onMouseDown', 221 'onMouseEnter', 222 'onMouseLeave', 223 'onMouseMove', 224 'onMouseOut', 225 'onMouseOver', 226 'onMouseUp', 227 'onSelect', 228 'onTouchCancel', 229 'onTouchEnd', 230 'onTouchMove', 231 'onTouchStart', 232 'onScroll', 233 'onWheel', 234 'onAbort', 235 'onCanPlay', 236 'onCanPlayThrough', 237 'onDurationChange', 238 'onEmptied', 239 'onEncrypted', 240 'onEnded', 241 'onError', 242 'onLoadedData', 243 'onLoadedMetadata', 244 'onLoadStart', 245 'onPause', 246 'onPlay', 247 'onPlaying', 248 'onProgress', 249 'onRateChange', 250 'onSeeked', 251 'onSeeking', 252 'onStalled', 253 'onSuspend', 254 'onTimeUpdate', 255 'onVolumeChange', 256 'onWaiting', 257 'onLoad', 258 'onError', 259 'onAnimationStart', 260 'onAnimationEnd', 261 'onAnimationIteration', 262 'onTransitionEnd', 263] 264*/ 265``` 266 267Contains a flat list of common event handler props used in JSX to attach behaviors 268to DOM events. 269 270#### eventHandlersByType 271 272The same list as `eventHandlers`, grouped into types. 273 274```js 275console.log(eventHandlersByType); 276/* 277{ 278 clipboard: [ 'onCopy', 'onCut', 'onPaste' ], 279 composition: [ 'onCompositionEnd', 'onCompositionStart', 'onCompositionUpdate' ], 280 keyboard: [ 'onKeyDown', 'onKeyPress', 'onKeyUp' ], 281 focus: [ 'onFocus', 'onBlur' ], 282 form: [ 'onChange', 'onInput', 'onSubmit' ], 283 mouse: [ 'onClick', 'onContextMenu', 'onDblClick', 'onDoubleClick', 'onDrag', 'onDragEnd', 'onDragEnter', 'onDragExit', 'onDragLeave', 'onDragOver', 'onDragStart', 'onDrop', 'onMouseDown', 'onMouseEnter', 'onMouseLeave', 'onMouseMove', 'onMouseOut', 'onMouseOver', 'onMouseUp' ], 284 selection: [ 'onSelect' ], 285 touch: [ 'onTouchCancel', 'onTouchEnd', 'onTouchMove', 'onTouchStart' ], 286 ui: [ 'onScroll' ], 287 wheel: [ 'onWheel' ], 288 media: [ 'onAbort', 'onCanPlay', 'onCanPlayThrough', 'onDurationChange', 'onEmptied', 'onEncrypted', 'onEnded', 'onError', 'onLoadedData', 'onLoadedMetadata', 'onLoadStart', 'onPause', 'onPlay', 'onPlaying', 'onProgress', 'onRateChange', 'onSeeked', 'onSeeking', 'onStalled', 'onSuspend', 'onTimeUpdate', 'onVolumeChange', 'onWaiting' ], 289 image: [ 'onLoad', 'onError' ], 290 animation: [ 'onAnimationStart', 'onAnimationEnd', 'onAnimationIteration' ], 291 transition: [ 'onTransitionEnd' ], 292} 293*/ 294``` 295