prettier
Advanced tools
Comparing version 0.15.0 to 0.16.0
@@ -0,1 +1,26 @@ | ||
# 0.16.0 | ||
[link](https://github.com/jlongster/prettier/compare/0.15.0...0.16.0) | ||
* Revert "Print \x and \u escapes in strings and regexes lowercase (#522) | ||
* Fix ternary indent bug (#577) | ||
* jsx parentheses fix (#580) | ||
* Run prettier on 0.15.0 (#558) | ||
* Add parenthesis around single argument arrow if comments (#573) | ||
* Use breakParent inside of last arrow expansion (#559) | ||
* Support dangling comments in ClassBody (#570) | ||
* Make all the member expressions but the last one part of the first group (#589) | ||
* Break long imports (#590) | ||
* Remove the concept of globalPrecedingNode (#561) | ||
* Remove test.js and put it back in the gitignore | ||
* Fix use strict as expression statement (#602) | ||
* Use arrow function when inputted that way for flow objects (#608) | ||
* Better support try/catch comments (#607) | ||
* Print CallExpression comments inside of memberChain (#600) | ||
* Do not attach comments to EmptyStatement (#599) | ||
* Fix files with only comments on the flow parser (#598) | ||
* Remove first line special case (#597) | ||
* Fix single indented JSX comment (#596) | ||
* Print dangling on ast on all the paths | ||
# 0.15.0 | ||
@@ -2,0 +27,0 @@ |
@@ -42,5 +42,6 @@ "use strict"; | ||
function attachComments(text, ast, opts) { | ||
if (ast.comments) { | ||
comments.attach(ast.comments, ast, text); | ||
ast.comments = []; | ||
const astComments = ast.comments; | ||
if (astComments) { | ||
delete ast.comments; | ||
comments.attach(astComments, ast, text); | ||
} | ||
@@ -47,0 +48,0 @@ ast.tokens = []; |
{ | ||
"name": "prettier", | ||
"version": "0.15.0", | ||
"version": "0.16.0", | ||
"description": "Prettier is an opinionated JavaScript formatter", | ||
@@ -5,0 +5,0 @@ "bin": { |
@@ -31,3 +31,3 @@ var assert = require("assert"); | ||
if (resultArray) { | ||
if (n.Node.check(node)) { | ||
if (n.Node.check(node) && node.type !== "EmptyStatement") { | ||
// This reverse insertion sort almost always takes constant | ||
@@ -90,9 +90,2 @@ // time because we almost always (maybe always?) append the | ||
if (middle > 0) { | ||
// Store the global preceding node separately from | ||
// `precedingNode` because they mean different things. This is | ||
// the previous node, ignoring any delimiters/blocks/etc. | ||
comment.globalPrecedingNode = childNodes[middle - 1]; | ||
} | ||
decorateComment(child, comment, text); | ||
@@ -145,15 +138,15 @@ return; // Abandon the binary search at this level. | ||
const precedingNode = comment.precedingNode; | ||
const globalPrecedingNode = comment.globalPrecedingNode; | ||
const enclosingNode = comment.enclosingNode; | ||
const followingNode = comment.followingNode; | ||
const isStartOfFile = comment.loc.start.line === 1; | ||
if ( | ||
util.hasNewline(text, locStart(comment), { backwards: true }) || | ||
isStartOfFile | ||
util.hasNewline(text, locStart(comment), { backwards: true }) | ||
) { | ||
// If a comment exists on its own line, prefer a leading comment. | ||
// We also need to check if it's the first line of the file. | ||
if (handleMemberExpressionComment(enclosingNode, followingNode, comment) || | ||
handleIfStatementComments(enclosingNode, followingNode, comment)) { | ||
if ( | ||
handleMemberExpressionComment(enclosingNode, followingNode, comment) || | ||
handleIfStatementComments(enclosingNode, followingNode, comment) || | ||
handleTryStatementComments(enclosingNode, followingNode, comment) | ||
) { | ||
// We're good | ||
@@ -168,16 +161,17 @@ } else if (followingNode) { | ||
} else { | ||
// TODO: If there are no nodes at all, we should still somehow | ||
// print the comment. | ||
// There are no nodes, let's attach it to the root of the ast | ||
addDanglingComment(ast, comment); | ||
} | ||
} else if (util.hasNewline(text, locEnd(comment))) { | ||
// There is content before this comment on the same line, but | ||
// none after it, so prefer a trailing comment. A trailing | ||
// comment *always* attaches itself to the previous node, no | ||
// matter if there's any syntax between them. | ||
const lastNode = precedingNode || globalPrecedingNode; | ||
if (lastNode) { | ||
// Always a trailing comment | ||
addTrailingComment(lastNode, comment); | ||
// none after it, so prefer a trailing comment of the previous node. | ||
if (precedingNode) { | ||
addTrailingComment(precedingNode, comment); | ||
} else if (followingNode) { | ||
addLeadingComment(followingNode, comment); | ||
} else if (enclosingNode) { | ||
addDanglingComment(enclosingNode, comment); | ||
} else { | ||
throw new Error("Preceding node not found"); | ||
// There are no nodes, let's attach it to the root of the ast | ||
addDanglingComment(ast, comment); | ||
} | ||
@@ -205,2 +199,5 @@ } else { | ||
addDanglingComment(enclosingNode, comment); | ||
} else { | ||
// There are no nodes, let's attach it to the root of the ast | ||
addDanglingComment(ast, comment); | ||
} | ||
@@ -296,2 +293,10 @@ } | ||
function addBlockOrNotComment(node, comment) { | ||
if (node.type === "BlockStatement") { | ||
addBlockStatementFirstComment(node, comment); | ||
} else { | ||
addLeadingComment(node, comment); | ||
} | ||
} | ||
// There are often comments before the else clause of if statements like | ||
@@ -311,6 +316,8 @@ // | ||
// // comment | ||
// ... | ||
// ... | ||
// } | ||
function handleIfStatementComments(enclosingNode, followingNode, comment) { | ||
if (!enclosingNode || enclosingNode.type !== "IfStatement" || !followingNode) { | ||
if ( | ||
!enclosingNode || enclosingNode.type !== "IfStatement" || !followingNode | ||
) { | ||
return false; | ||
@@ -325,7 +332,3 @@ } | ||
if (followingNode.type === "IfStatement") { | ||
if (followingNode.consequent.type === "BlockStatement") { | ||
addBlockStatementFirstComment(followingNode.consequent, comment); | ||
} else { | ||
addLeadingComment(followingNode.consequent, comment); | ||
} | ||
addBlockOrNotComment(followingNode.consequent, comment); | ||
return true; | ||
@@ -337,7 +340,35 @@ } | ||
// Same as IfStatement but for TryStatement | ||
function handleTryStatementComments(enclosingNode, followingNode, comment) { | ||
if ( | ||
!enclosingNode || enclosingNode.type !== "TryStatement" || !followingNode | ||
) { | ||
return false; | ||
} | ||
if (followingNode.type === "BlockStatement") { | ||
addBlockStatementFirstComment(followingNode, comment); | ||
return true; | ||
} | ||
if (followingNode.type === "TryStatement") { | ||
addBlockOrNotComment(followingNode.finalizer, comment); | ||
return true; | ||
} | ||
if (followingNode.type === "CatchClause") { | ||
addBlockOrNotComment(followingNode.body, comment); | ||
return true; | ||
} | ||
return false; | ||
} | ||
function handleMemberExpressionComment(enclosingNode, followingNode, comment) { | ||
if (enclosingNode && | ||
if ( | ||
enclosingNode && | ||
enclosingNode.type === "MemberExpression" && | ||
followingNode && | ||
followingNode.type === "Identifier") { | ||
followingNode.type === "Identifier" | ||
) { | ||
addLeadingComment(enclosingNode, comment); | ||
@@ -388,7 +419,5 @@ return true; | ||
if ( | ||
util.hasNewline(options.originalText, locStart(comment), { | ||
if (util.hasNewline(options.originalText, locStart(comment), { | ||
backwards: true | ||
}) | ||
) { | ||
})) { | ||
// This allows comments at the end of nested structures: | ||
@@ -395,0 +424,0 @@ // { |
@@ -500,2 +500,7 @@ var assert = require("assert"); | ||
case "StringLiteral": | ||
if (parent.type === "ExpressionStatement") { | ||
return true; | ||
} | ||
default: | ||
@@ -502,0 +507,0 @@ if ( |
222
test.js
@@ -1,1 +0,221 @@ | ||
import someCoolUtilWithARatherLongName from '../../../../utils/someCoolUtilWithARatherLongName'; | ||
class UserInfo extends React.Component { | ||
props: Props; | ||
state: void; | ||
_info: ?Info = null; | ||
static defaultProps = { | ||
showActions: true, | ||
showAvailability: true, | ||
}; | ||
render(): ?React.Element<*> { | ||
if (!this.props.user) { | ||
return null; | ||
} | ||
const user: User = this.props.user; | ||
if (!this.props.user.full_name) { | ||
return ( | ||
<View style={styles.loading}> | ||
<FBLoadingIndicator /> | ||
</View> | ||
); | ||
} | ||
// title | ||
const title = user.full_name; | ||
// subtitle | ||
let subtitle = ''; | ||
if (user.work_campus && user.work_building && user.work_floor) { | ||
const campus = (user.work_campus || ''); | ||
const building = (user.work_building || '') | ||
.replace(campus, '') | ||
.replace(/^0+/, ''); | ||
const floor = (user.work_floor || '') | ||
.replace(/^0+/, ''); | ||
const location = (user.work_desk || ''); | ||
subtitle = `${campus} ${building}.${floor} ${location}`; | ||
} | ||
// actions | ||
const actions: Array<Action> = [ | ||
// TODO: add this button back in when routing is implemented | ||
// { | ||
// type: 'outline-primary', | ||
// title: 'Route', | ||
// glyphName: 'directions', | ||
// glyphSize: '16', | ||
// onPress: this._onPressRoute, | ||
// }, | ||
]; | ||
// Messenger integration is only available on iOS | ||
if (Platform.OS === 'ios') { | ||
actions.push({ | ||
type: 'outline-primary', | ||
title: 'Message', | ||
glyphName: 'messages', | ||
glyphSize: '16', | ||
onPress: this._onPressMessage, | ||
}); | ||
} | ||
actions.push({ | ||
title: 'Meeting', | ||
glyphName: 'calendar', | ||
glyphSize: '16', | ||
onPress: this._onPressMeeting, | ||
}); | ||
// left | ||
const left = ( | ||
<Image | ||
style={styles.picture} | ||
source={ | ||
user.profile_picture || | ||
require('./images/user_placeholder.png') | ||
} | ||
/> | ||
); | ||
// right | ||
const status = user.current_status_availability; | ||
const right = ( | ||
<View style={styles.availability}> | ||
<Text | ||
style={[ | ||
styles.availabilityText, | ||
status === 'NORMAL' && styles.statusNormal, | ||
status === 'SEMI_AVAILABLE' && styles.statusSemiAvailable, | ||
status === 'OFF_THE_GRID' && styles.statusOffTheGrid, | ||
]}> | ||
{ | ||
status === 'NORMAL' && 'Available' || | ||
status === 'SEMI_AVAILABLE' && 'Sporadic' || | ||
status === 'OFF_THE_GRID' && 'Off the Grid' || | ||
'' | ||
} | ||
</Text> | ||
</View> | ||
); | ||
return ( | ||
<Info | ||
ref={ref => {this._info = ref;}} | ||
title={title} | ||
subtitle={subtitle} | ||
availability={user.current_status_availability} | ||
left={left} | ||
right={this.props.showAvailability ? right : null} | ||
actions={this.props.showActions ? actions : []} | ||
onPress={this._onPressHeader} | ||
/> | ||
); | ||
} | ||
hide(): void { | ||
if (this._info) { | ||
this._info.hide(); | ||
} | ||
} | ||
_onPressHeader = (): void => { | ||
if (this.props.user && this.props.user.unencoded_id) { | ||
Events.navigateToUser(this.props.user.unencoded_id); | ||
} | ||
}; | ||
_onPressRoute(): void { | ||
if (this.props.user && this.props.user.id) { | ||
Events.navigateToWayfinder({user: this.props.user.id}); | ||
} | ||
} | ||
_onPressMeeting = (): void => { | ||
if (this.props.user && this.props.user.unencoded_id) { | ||
Events.navigateToNewMeeting({}, { | ||
inviteeIDs: [this.props.user.unencoded_id], | ||
}); | ||
} | ||
}; | ||
_onPressMessage = (): void => { | ||
if (this.props.user) { | ||
// prefer messaging the @work user, if there is one | ||
const id = | ||
this.props.user.work_user && | ||
this.props.user.work_user.id || | ||
this.props.user.unencoded_id || | ||
''; | ||
if (id) { | ||
Linking.openURL(`fb-messenger://user-thread/${id}`); | ||
} | ||
} | ||
}; | ||
} | ||
const styles = StyleSheet.create({ | ||
picture: { | ||
width: 40, | ||
height: 40, | ||
backgroundColor: 'rgb(196,210,231)', | ||
borderRadius: 2, | ||
resizeMode: 'cover', | ||
}, | ||
availability: { | ||
flex: 1, | ||
width: 92, | ||
justifyContent: 'center', | ||
}, | ||
availabilityText: { | ||
...UFIGFontInternal.font('bold', 12), | ||
textAlign: 'right', | ||
}, | ||
statusNormal: { | ||
color: Constants.Colors.Vibrant.NORMAL, | ||
}, | ||
statusSemiAvailable: { | ||
color: Constants.Colors.Vibrant.SEMI_AVAILABLE, | ||
}, | ||
statusOffTheGrid: { | ||
color: Constants.Colors.Vibrant.OFF_THE_GRID, | ||
}, | ||
loading: { | ||
alignItems: 'center', | ||
justifyContent: 'center', | ||
padding: 10, | ||
backgroundColor: UFIGColorPalette.white, | ||
borderTopWidth: StyleSheet.hairlineWidth, | ||
borderTopColor: 'rgba(0, 0, 0, 0.1)', | ||
}, | ||
}); | ||
module.exports = Relay.createContainer( | ||
UserInfo, | ||
{ | ||
fragments: { | ||
user: () => Relay.QL` | ||
fragment on Employee { | ||
id | ||
unencoded_id | ||
full_name | ||
work_campus | ||
work_building | ||
work_floor | ||
work_desk | ||
current_status_availability | ||
profile_picture { | ||
uri | ||
} | ||
work_user { | ||
id | ||
} | ||
} | ||
`, | ||
}, | ||
}, | ||
); |
Sorry, the diff of this file is too big to display
Sorry, the diff of this file is too big to display
1054601
7406