[analyzer_plugin] consistent hashCode for SourceFileEdit

Fixes #49371

Change-Id: I853323df821a9b6481f6fdd190ccecba2c01aa2b
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/250380
Commit-Queue: Brian Wilkerson <brianwilkerson@google.com>
Reviewed-by: Brian Wilkerson <brianwilkerson@google.com>
This commit is contained in:
Ahmed Ashour 2022-07-06 16:03:20 +00:00 committed by Commit Bot
parent 7df3cd3cfd
commit 572f24882f
7 changed files with 510 additions and 839 deletions

File diff suppressed because it is too large Load diff

View file

@ -257,7 +257,7 @@ class CodegenProtocolVisitor extends DartCodegenVisitor with CodeGenerator {
/// Emit the toJson() code for an empty class.
void emitEmptyToJsonMember() {
writeln('@override');
writeln('Map<String, Object> toJson() => <String, Object>{};');
writeln('Map<String, Object> toJson() => {};');
}
/// Emit a class to encapsulate an enum.
@ -522,19 +522,22 @@ class CodegenProtocolVisitor extends DartCodegenVisitor with CodeGenerator {
/// Emit the operator== code for an object class.
void emitObjectEqualsMember(TypeObject? type, String className) {
writeln('@override');
writeln('bool operator ==(other) {');
write('bool operator ==(other) ');
if (type == null) {
writeln('=> other is $className;');
return;
}
writeln('{');
indent(() {
writeln('if (other is $className) {');
indent(() {
var comparisons = <String>[];
if (type != null) {
for (var field in type.fields) {
if (field.value != null) {
continue;
}
comparisons.add(compareEqualsCode(
field.type, field.name, 'other.${field.name}'));
for (var field in type.fields) {
if (field.value != null) {
continue;
}
comparisons.add(
compareEqualsCode(field.type, field.name, 'other.${field.name}'));
}
if (comparisons.isEmpty) {
writeln('return true;');
@ -639,27 +642,44 @@ class CodegenProtocolVisitor extends DartCodegenVisitor with CodeGenerator {
void emitObjectHashCode(TypeObject? type, String className) {
writeln('@override');
writeln('int get hashCode => ');
String hashAll(String value) => 'Object.hashAll($value)';
String fieldValue(TypeObjectField field, {required bool single}) {
if (field.value != null) {
return field.value.hashCode.toString();
} else {
var name = field.name;
var type = field.type;
if (type is TypeList) {
var nullableString = field.optional ? ' ?? []' : '';
return hashAll(name + nullableString);
} else if (type is TypeMap) {
var nullable = field.optional ? '?' : '';
return hashAll(
'[...$nullable$name$nullable.keys,'
' ...$nullable$name$nullable.values]',
);
}
return single ? '$name.hashCode' : name;
}
}
indent(() {
if (type == null) {
writeln(' ${className.hashCode}');
} else {
final items = type.fields.map((field) {
if (field.value != null) {
return field.value.hashCode.toString();
} else {
return field.name;
}
}).toList();
if (items.isEmpty) {
final fields = type.fields;
if (fields.isEmpty) {
writeln('0');
} else if (items.length == 1) {
write(items.single);
write('.hashCode');
} else if (fields.length == 1) {
var field = fields.single;
write(fieldValue(field, single: true));
} else {
writeln('Object.hash(');
for (var field in items) {
writeln('$field,');
for (var field in fields) {
write(fieldValue(field, single: false));
writeln(',');
}
writeln(')');
}

View file

@ -259,7 +259,7 @@ class AnalysisError implements HasToJson {
correction,
code,
url,
contextMessages,
Object.hashAll(contextMessages ?? []),
hasFix,
);
}
@ -476,7 +476,7 @@ class ChangeContentOverlay implements HasToJson {
@override
int get hashCode => Object.hash(
873118866,
edits,
Object.hashAll(edits),
);
}
@ -977,11 +977,11 @@ class CompletionSuggestion implements HasToJson {
docComplete,
declaringType,
defaultArgumentListString,
defaultArgumentListTextRanges,
Object.hashAll(defaultArgumentListTextRanges ?? []),
element,
returnType,
parameterNames,
parameterTypes,
Object.hashAll(parameterNames ?? []),
Object.hashAll(parameterTypes ?? []),
requiredParameterCount,
hasNamedParameters,
parameterName,
@ -2593,7 +2593,7 @@ class KytheEntry implements HasToJson {
kind,
target,
fact,
value,
Object.hashAll(value ?? []),
);
}
@ -2811,9 +2811,9 @@ class LinkedEditGroup implements HasToJson {
@override
int get hashCode => Object.hash(
positions,
Object.hashAll(positions),
length,
suggestions,
Object.hashAll(suggestions),
);
}
@ -3168,7 +3168,7 @@ class NavigationRegion implements HasToJson {
int get hashCode => Object.hash(
offset,
length,
targets,
Object.hashAll(targets),
);
}
@ -3407,7 +3407,7 @@ class Occurrences implements HasToJson {
@override
int get hashCode => Object.hash(
element,
offsets,
Object.hashAll(offsets),
length,
);
}
@ -3543,7 +3543,7 @@ class Outline implements HasToJson {
length,
codeOffset,
codeLength,
children,
Object.hashAll(children ?? []),
);
}
@ -4266,7 +4266,7 @@ class RemoveContentOverlay implements HasToJson {
}
@override
int get hashCode => 114870849.hashCode;
int get hashCode => 114870849;
}
/// SourceChange
@ -4436,8 +4436,8 @@ class SourceChange implements HasToJson {
@override
int get hashCode => Object.hash(
message,
edits,
linkedEditGroups,
Object.hashAll(edits),
Object.hashAll(linkedEditGroups),
selection,
selectionLength,
id,
@ -4659,6 +4659,6 @@ class SourceFileEdit implements HasToJson {
int get hashCode => Object.hash(
file,
fileStamp,
edits,
Object.hashAll(edits),
);
}

View file

@ -259,7 +259,7 @@ class AnalysisError implements HasToJson {
correction,
code,
url,
contextMessages,
Object.hashAll(contextMessages ?? []),
hasFix,
);
}
@ -476,7 +476,7 @@ class ChangeContentOverlay implements HasToJson {
@override
int get hashCode => Object.hash(
873118866,
edits,
Object.hashAll(edits),
);
}
@ -977,11 +977,11 @@ class CompletionSuggestion implements HasToJson {
docComplete,
declaringType,
defaultArgumentListString,
defaultArgumentListTextRanges,
Object.hashAll(defaultArgumentListTextRanges ?? []),
element,
returnType,
parameterNames,
parameterTypes,
Object.hashAll(parameterNames ?? []),
Object.hashAll(parameterTypes ?? []),
requiredParameterCount,
hasNamedParameters,
parameterName,
@ -2593,7 +2593,7 @@ class KytheEntry implements HasToJson {
kind,
target,
fact,
value,
Object.hashAll(value ?? []),
);
}
@ -2811,9 +2811,9 @@ class LinkedEditGroup implements HasToJson {
@override
int get hashCode => Object.hash(
positions,
Object.hashAll(positions),
length,
suggestions,
Object.hashAll(suggestions),
);
}
@ -3168,7 +3168,7 @@ class NavigationRegion implements HasToJson {
int get hashCode => Object.hash(
offset,
length,
targets,
Object.hashAll(targets),
);
}
@ -3407,7 +3407,7 @@ class Occurrences implements HasToJson {
@override
int get hashCode => Object.hash(
element,
offsets,
Object.hashAll(offsets),
length,
);
}
@ -3543,7 +3543,7 @@ class Outline implements HasToJson {
length,
codeOffset,
codeLength,
children,
Object.hashAll(children ?? []),
);
}
@ -4266,7 +4266,7 @@ class RemoveContentOverlay implements HasToJson {
}
@override
int get hashCode => 114870849.hashCode;
int get hashCode => 114870849;
}
/// SourceChange
@ -4436,8 +4436,8 @@ class SourceChange implements HasToJson {
@override
int get hashCode => Object.hash(
message,
edits,
linkedEditGroups,
Object.hashAll(edits),
Object.hashAll(linkedEditGroups),
selection,
selectionLength,
id,
@ -4659,6 +4659,6 @@ class SourceFileEdit implements HasToJson {
int get hashCode => Object.hash(
file,
fileStamp,
edits,
Object.hashAll(edits),
);
}

View file

@ -84,7 +84,7 @@ class AnalysisErrorFixes implements HasToJson {
@override
int get hashCode => Object.hash(
error,
fixes,
Object.hashAll(fixes),
);
}
@ -165,7 +165,7 @@ class AnalysisErrorsParams implements HasToJson {
@override
int get hashCode => Object.hash(
file,
errors,
Object.hashAll(errors),
);
}
@ -246,7 +246,7 @@ class AnalysisFoldingParams implements HasToJson {
@override
int get hashCode => Object.hash(
file,
regions,
Object.hashAll(regions),
);
}
@ -443,9 +443,9 @@ class AnalysisGetNavigationResult implements ResponseResult {
@override
int get hashCode => Object.hash(
files,
targets,
regions,
Object.hashAll(files),
Object.hashAll(targets),
Object.hashAll(regions),
);
}
@ -514,7 +514,7 @@ class AnalysisHandleWatchEventsParams implements RequestParams {
}
@override
int get hashCode => events.hashCode;
int get hashCode => Object.hashAll(events);
}
/// analysis.handleWatchEvents result
@ -522,7 +522,7 @@ class AnalysisHandleWatchEventsParams implements RequestParams {
/// Clients may not extend, implement or mix-in this class.
class AnalysisHandleWatchEventsResult implements ResponseResult {
@override
Map<String, Object> toJson() => <String, Object>{};
Map<String, Object> toJson() => {};
@override
Response toResponse(String id, int requestTime) {
@ -530,12 +530,7 @@ class AnalysisHandleWatchEventsResult implements ResponseResult {
}
@override
bool operator ==(other) {
if (other is AnalysisHandleWatchEventsResult) {
return true;
}
return false;
}
bool operator ==(other) => other is AnalysisHandleWatchEventsResult;
@override
int get hashCode => 779767607;
@ -618,7 +613,7 @@ class AnalysisHighlightsParams implements HasToJson {
@override
int get hashCode => Object.hash(
file,
regions,
Object.hashAll(regions),
);
}
@ -732,9 +727,9 @@ class AnalysisNavigationParams implements HasToJson {
@override
int get hashCode => Object.hash(
file,
regions,
targets,
files,
Object.hashAll(regions),
Object.hashAll(targets),
Object.hashAll(files),
);
}
@ -816,7 +811,7 @@ class AnalysisOccurrencesParams implements HasToJson {
@override
int get hashCode => Object.hash(
file,
occurrences,
Object.hashAll(occurrences),
);
}
@ -895,7 +890,7 @@ class AnalysisOutlineParams implements HasToJson {
@override
int get hashCode => Object.hash(
file,
outline,
Object.hashAll(outline),
);
}
@ -1033,7 +1028,7 @@ class AnalysisSetContextRootsParams implements RequestParams {
}
@override
int get hashCode => roots.hashCode;
int get hashCode => Object.hashAll(roots);
}
/// analysis.setContextRoots result
@ -1041,7 +1036,7 @@ class AnalysisSetContextRootsParams implements RequestParams {
/// Clients may not extend, implement or mix-in this class.
class AnalysisSetContextRootsResult implements ResponseResult {
@override
Map<String, Object> toJson() => <String, Object>{};
Map<String, Object> toJson() => {};
@override
Response toResponse(String id, int requestTime) {
@ -1049,12 +1044,7 @@ class AnalysisSetContextRootsResult implements ResponseResult {
}
@override
bool operator ==(other) {
if (other is AnalysisSetContextRootsResult) {
return true;
}
return false;
}
bool operator ==(other) => other is AnalysisSetContextRootsResult;
@override
int get hashCode => 969645618;
@ -1120,7 +1110,7 @@ class AnalysisSetPriorityFilesParams implements RequestParams {
}
@override
int get hashCode => files.hashCode;
int get hashCode => Object.hashAll(files);
}
/// analysis.setPriorityFiles result
@ -1128,7 +1118,7 @@ class AnalysisSetPriorityFilesParams implements RequestParams {
/// Clients may not extend, implement or mix-in this class.
class AnalysisSetPriorityFilesResult implements ResponseResult {
@override
Map<String, Object> toJson() => <String, Object>{};
Map<String, Object> toJson() => {};
@override
Response toResponse(String id, int requestTime) {
@ -1136,12 +1126,7 @@ class AnalysisSetPriorityFilesResult implements ResponseResult {
}
@override
bool operator ==(other) {
if (other is AnalysisSetPriorityFilesResult) {
return true;
}
return false;
}
bool operator ==(other) => other is AnalysisSetPriorityFilesResult;
@override
int get hashCode => 330050055;
@ -1217,7 +1202,8 @@ class AnalysisSetSubscriptionsParams implements RequestParams {
}
@override
int get hashCode => subscriptions.hashCode;
int get hashCode =>
Object.hashAll([...subscriptions.keys, ...subscriptions.values]);
}
/// analysis.setSubscriptions result
@ -1225,7 +1211,7 @@ class AnalysisSetSubscriptionsParams implements RequestParams {
/// Clients may not extend, implement or mix-in this class.
class AnalysisSetSubscriptionsResult implements ResponseResult {
@override
Map<String, Object> toJson() => <String, Object>{};
Map<String, Object> toJson() => {};
@override
Response toResponse(String id, int requestTime) {
@ -1233,12 +1219,7 @@ class AnalysisSetSubscriptionsResult implements ResponseResult {
}
@override
bool operator ==(other) {
if (other is AnalysisSetSubscriptionsResult) {
return true;
}
return false;
}
bool operator ==(other) => other is AnalysisSetSubscriptionsResult;
@override
int get hashCode => 218088493;
@ -1315,7 +1296,7 @@ class AnalysisUpdateContentParams implements RequestParams {
}
@override
int get hashCode => files.hashCode;
int get hashCode => Object.hashAll([...files.keys, ...files.values]);
}
/// analysis.updateContent result
@ -1323,7 +1304,7 @@ class AnalysisUpdateContentParams implements RequestParams {
/// Clients may not extend, implement or mix-in this class.
class AnalysisUpdateContentResult implements ResponseResult {
@override
Map<String, Object> toJson() => <String, Object>{};
Map<String, Object> toJson() => {};
@override
Response toResponse(String id, int requestTime) {
@ -1331,12 +1312,7 @@ class AnalysisUpdateContentResult implements ResponseResult {
}
@override
bool operator ==(other) {
if (other is AnalysisUpdateContentResult) {
return true;
}
return false;
}
bool operator ==(other) => other is AnalysisUpdateContentResult;
@override
int get hashCode => 468798730;
@ -1526,7 +1502,7 @@ class CompletionGetSuggestionsResult implements ResponseResult {
int get hashCode => Object.hash(
replacementOffset,
replacementLength,
results,
Object.hashAll(results),
);
}
@ -1610,7 +1586,7 @@ class ContextRoot implements HasToJson {
@override
int get hashCode => Object.hash(
root,
exclude,
Object.hashAll(exclude),
optionsFile,
);
}
@ -1621,12 +1597,7 @@ class ContextRoot implements HasToJson {
class ConvertGetterToMethodFeedback extends RefactoringFeedback
implements HasToJson {
@override
bool operator ==(other) {
if (other is ConvertGetterToMethodFeedback) {
return true;
}
return false;
}
bool operator ==(other) => other is ConvertGetterToMethodFeedback;
@override
int get hashCode => 616032599;
@ -1638,12 +1609,7 @@ class ConvertGetterToMethodFeedback extends RefactoringFeedback
class ConvertGetterToMethodOptions extends RefactoringOptions
implements HasToJson {
@override
bool operator ==(other) {
if (other is ConvertGetterToMethodOptions) {
return true;
}
return false;
}
bool operator ==(other) => other is ConvertGetterToMethodOptions;
@override
int get hashCode => 488848400;
@ -1655,12 +1621,7 @@ class ConvertGetterToMethodOptions extends RefactoringOptions
class ConvertMethodToGetterFeedback extends RefactoringFeedback
implements HasToJson {
@override
bool operator ==(other) {
if (other is ConvertMethodToGetterFeedback) {
return true;
}
return false;
}
bool operator ==(other) => other is ConvertMethodToGetterFeedback;
@override
int get hashCode => 165291526;
@ -1672,12 +1633,7 @@ class ConvertMethodToGetterFeedback extends RefactoringFeedback
class ConvertMethodToGetterOptions extends RefactoringOptions
implements HasToJson {
@override
bool operator ==(other) {
if (other is ConvertMethodToGetterOptions) {
return true;
}
return false;
}
bool operator ==(other) => other is ConvertMethodToGetterOptions;
@override
int get hashCode => 27952290;
@ -1838,7 +1794,7 @@ class EditGetAssistsResult implements ResponseResult {
}
@override
int get hashCode => assists.hashCode;
int get hashCode => Object.hashAll(assists);
}
/// edit.getAvailableRefactorings params
@ -2003,7 +1959,7 @@ class EditGetAvailableRefactoringsResult implements ResponseResult {
}
@override
int get hashCode => kinds.hashCode;
int get hashCode => Object.hashAll(kinds);
}
/// edit.getFixes params
@ -2147,7 +2103,7 @@ class EditGetFixesResult implements ResponseResult {
}
@override
int get hashCode => fixes.hashCode;
int get hashCode => Object.hashAll(fixes);
}
/// edit.getRefactoring params
@ -2462,12 +2418,12 @@ class EditGetRefactoringResult implements ResponseResult {
@override
int get hashCode => Object.hash(
initialProblems,
optionsProblems,
finalProblems,
Object.hashAll(initialProblems),
Object.hashAll(optionsProblems),
Object.hashAll(finalProblems),
feedback,
change,
potentialEdits,
Object.hashAll(potentialEdits ?? []),
);
}
@ -2591,11 +2547,11 @@ class ExtractLocalVariableFeedback extends RefactoringFeedback {
@override
int get hashCode => Object.hash(
coveringExpressionOffsets,
coveringExpressionLengths,
names,
offsets,
lengths,
Object.hashAll(coveringExpressionOffsets ?? []),
Object.hashAll(coveringExpressionLengths ?? []),
Object.hashAll(names),
Object.hashAll(offsets),
Object.hashAll(lengths),
);
}
@ -2836,11 +2792,11 @@ class ExtractMethodFeedback extends RefactoringFeedback {
offset,
length,
returnType,
names,
Object.hashAll(names),
canCreateGetter,
parameters,
offsets,
lengths,
Object.hashAll(parameters),
Object.hashAll(offsets),
Object.hashAll(lengths),
);
}
@ -2978,7 +2934,7 @@ class ExtractMethodOptions extends RefactoringOptions {
returnType,
createGetter,
name,
parameters,
Object.hashAll(parameters),
extractAll,
);
}
@ -3056,12 +3012,7 @@ class InlineLocalVariableFeedback extends RefactoringFeedback {
class InlineLocalVariableOptions extends RefactoringOptions
implements HasToJson {
@override
bool operator ==(other) {
if (other is InlineLocalVariableOptions) {
return true;
}
return false;
}
bool operator ==(other) => other is InlineLocalVariableOptions;
@override
int get hashCode => 540364977;
@ -3375,8 +3326,8 @@ class KytheGetKytheEntriesResult implements ResponseResult {
@override
int get hashCode => Object.hash(
entries,
files,
Object.hashAll(entries),
Object.hashAll(files),
);
}
@ -3385,12 +3336,7 @@ class KytheGetKytheEntriesResult implements ResponseResult {
/// Clients may not extend, implement or mix-in this class.
class MoveFileFeedback extends RefactoringFeedback implements HasToJson {
@override
bool operator ==(other) {
if (other is MoveFileFeedback) {
return true;
}
return false;
}
bool operator ==(other) => other is MoveFileFeedback;
@override
int get hashCode => 438975893;
@ -3554,7 +3500,7 @@ class PluginErrorParams implements HasToJson {
/// Clients may not extend, implement or mix-in this class.
class PluginShutdownParams implements RequestParams {
@override
Map<String, Object> toJson() => <String, Object>{};
Map<String, Object> toJson() => {};
@override
Request toRequest(String id) {
@ -3562,12 +3508,7 @@ class PluginShutdownParams implements RequestParams {
}
@override
bool operator ==(other) {
if (other is PluginShutdownParams) {
return true;
}
return false;
}
bool operator ==(other) => other is PluginShutdownParams;
@override
int get hashCode => 478064585;
@ -3578,7 +3519,7 @@ class PluginShutdownParams implements RequestParams {
/// Clients may not extend, implement or mix-in this class.
class PluginShutdownResult implements ResponseResult {
@override
Map<String, Object> toJson() => <String, Object>{};
Map<String, Object> toJson() => {};
@override
Response toResponse(String id, int requestTime) {
@ -3586,12 +3527,7 @@ class PluginShutdownResult implements ResponseResult {
}
@override
bool operator ==(other) {
if (other is PluginShutdownResult) {
return true;
}
return false;
}
bool operator ==(other) => other is PluginShutdownResult;
@override
int get hashCode => 9389109;
@ -3825,7 +3761,7 @@ class PluginVersionCheckResult implements ResponseResult {
name,
version,
contactInfo,
interestingFiles,
Object.hashAll(interestingFiles),
);
}

View file

@ -243,7 +243,7 @@ class CodegenProtocolVisitor extends DartCodegenVisitor with CodeGenerator {
/// Emit the toJson() code for an empty class.
void emitEmptyToJsonMember() {
writeln('@override');
writeln('Map<String, Object> toJson() => <String, Object>{};');
writeln('Map<String, Object> toJson() => {};');
}
/// Emit a class to encapsulate an enum.
@ -498,19 +498,22 @@ class CodegenProtocolVisitor extends DartCodegenVisitor with CodeGenerator {
/// Emit the operator== code for an object class.
void emitObjectEqualsMember(TypeObject? type, String className) {
writeln('@override');
writeln('bool operator ==(other) {');
write('bool operator ==(other) ');
if (type == null) {
writeln('=> other is $className;');
return;
}
writeln('{');
indent(() {
writeln('if (other is $className) {');
indent(() {
var comparisons = <String>[];
if (type != null) {
for (var field in type.fields) {
if (field.value != null) {
continue;
}
comparisons.add(compareEqualsCode(
field.type, field.name, 'other.${field.name}'));
for (var field in type.fields) {
if (field.value != null) {
continue;
}
comparisons.add(
compareEqualsCode(field.type, field.name, 'other.${field.name}'));
}
if (comparisons.isEmpty) {
writeln('return true;');
@ -614,33 +617,51 @@ class CodegenProtocolVisitor extends DartCodegenVisitor with CodeGenerator {
void emitObjectHashCode(TypeObject? type, String className) {
writeln('@override');
writeln('int get hashCode => ');
String hashAll(String value) => 'Object.hashAll($value)';
String fieldValue(TypeObjectField field, {required bool single}) {
if (field.value != null) {
return field.value.hashCode.toString();
} else {
var name = field.name;
var type = field.type;
if (type is TypeList) {
var nullableString = field.optional ? ' ?? []' : '';
return hashAll(name + nullableString);
} else if (type is TypeMap) {
var nullable = field.optional ? '?' : '';
return hashAll(
'[...$nullable$name$nullable.keys,'
' ...$nullable$name$nullable.values]',
);
}
return single ? '$name.hashCode' : name;
}
}
indent(() {
if (type == null) {
writeln(' ${className.hashCode}');
} else {
final items = type.fields.map((field) {
if (field.value != null) {
return field.value.hashCode.toString();
} else {
return field.name;
}
}).toList();
if (items.isEmpty) {
final fields = type.fields;
if (fields.isEmpty) {
writeln('0');
} else if (items.length == 1) {
write(items.single);
write('.hashCode');
} else if (items.length <= 20) {
} else if (fields.length == 1) {
var field = fields.single;
write(fieldValue(field, single: true));
} else if (fields.length <= 20) {
writeln('Object.hash(');
for (var field in items) {
writeln('$field,');
for (var field in fields) {
write(fieldValue(field, single: false));
writeln(',');
}
writeln(')');
} else {
writeln('Object.hashAll([');
for (var field in items) {
writeln('$field,');
for (var field in fields) {
write(fieldValue(field, single: false));
writeln(',');
}
writeln('])');
}