Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Sign in
Toggle navigation
F
Front-End
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
abdullh.alsoleman
Front-End
Commits
d2f889b4
Unverified
Commit
d2f889b4
authored
Mar 06, 2020
by
Jonah Williams
Committed by
GitHub
Mar 06, 2020
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
[flutter_tools] Reduce context usage in analyze command and tests (#49589)
parent
bafa03e5
Changes
10
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
10 changed files
with
565 additions
and
421 deletions
+565
-421
executable.dart
packages/flutter_tools/lib/executable.dart
+8
-1
analyze.dart
packages/flutter_tools/lib/src/commands/analyze.dart
+40
-2
analyze_base.dart
packages/flutter_tools/lib/src/commands/analyze_base.dart
+32
-22
analyze_continuously.dart
.../flutter_tools/lib/src/commands/analyze_continuously.dart
+40
-19
analyze_once.dart
packages/flutter_tools/lib/src/commands/analyze_once.dart
+36
-17
analysis.dart
packages/flutter_tools/lib/src/dart/analysis.dart
+56
-19
analyze_continuously_test.dart
...st/commands.shard/hermetic/analyze_continuously_test.dart
+57
-33
analyze_test.dart
...tter_tools/test/commands.shard/hermetic/analyze_test.dart
+17
-1
analyze_once_test.dart
...ools/test/commands.shard/permeable/analyze_once_test.dart
+279
-230
sdk_validation_test.dart
...er_tools/test/general.shard/dart/sdk_validation_test.dart
+0
-77
No files found.
packages/flutter_tools/lib/executable.dart
View file @
d2f889b4
...
...
@@ -67,7 +67,14 @@ Future<void> main(List<String> args) async {
final
bool
verboseHelp
=
help
&&
verbose
;
await
runner
.
run
(
args
,
<
FlutterCommand
>[
AnalyzeCommand
(
verboseHelp:
verboseHelp
),
AnalyzeCommand
(
verboseHelp:
verboseHelp
,
fileSystem:
globals
.
fs
,
platform:
globals
.
platform
,
processManager:
globals
.
processManager
,
logger:
globals
.
logger
,
terminal:
globals
.
terminal
,
),
AssembleCommand
(),
AttachCommand
(
verboseHelp:
verboseHelp
),
BuildCommand
(
verboseHelp:
verboseHelp
),
...
...
packages/flutter_tools/lib/src/commands/analyze.dart
View file @
d2f889b4
...
...
@@ -4,14 +4,32 @@
import
'dart:async'
;
import
'package:meta/meta.dart'
;
import
'package:platform/platform.dart'
;
import
'package:process/process.dart'
;
import
'../base/file_system.dart'
;
import
'../base/logger.dart'
;
import
'../base/terminal.dart'
;
import
'../globals.dart'
as
globals
;
import
'../runner/flutter_command.dart'
;
import
'analyze_continuously.dart'
;
import
'analyze_once.dart'
;
class
AnalyzeCommand
extends
FlutterCommand
{
AnalyzeCommand
({
bool
verboseHelp
=
false
,
this
.
workingDirectory
})
{
AnalyzeCommand
({
bool
verboseHelp
=
false
,
this
.
workingDirectory
,
@required
FileSystem
fileSystem
,
@required
Platform
platform
,
@required
AnsiTerminal
terminal
,
@required
Logger
logger
,
@required
ProcessManager
processManager
,
})
:
_fileSystem
=
fileSystem
,
_processManager
=
processManager
,
_logger
=
logger
,
_terminal
=
terminal
,
_platform
=
platform
{
argParser
.
addFlag
(
'flutter-repo'
,
negatable:
false
,
help:
'Include all the examples and tests from the Flutter repository.'
,
...
...
@@ -59,6 +77,12 @@ class AnalyzeCommand extends FlutterCommand {
/// The working directory for testing analysis using dartanalyzer.
final
Directory
workingDirectory
;
final
FileSystem
_fileSystem
;
final
Logger
_logger
;
final
AnsiTerminal
_terminal
;
final
ProcessManager
_processManager
;
final
Platform
_platform
;
@override
String
get
name
=>
'analyze'
;
...
...
@@ -73,7 +97,7 @@ class AnalyzeCommand extends FlutterCommand {
}
// Or we're not in a project directory.
if
(!
globals
.
fs
.
file
(
'pubspec.yaml'
).
existsSync
())
{
if
(!
_fileSystem
.
file
(
'pubspec.yaml'
).
existsSync
())
{
return
false
;
}
...
...
@@ -87,6 +111,13 @@ class AnalyzeCommand extends FlutterCommand {
argResults
,
runner
.
getRepoRoots
(),
runner
.
getRepoPackages
(),
fileSystem:
_fileSystem
,
// TODO(jonahwilliams): determine a better way to inject the logger,
// since it is constructed on-demand.
logger:
_logger
??
globals
.
logger
,
platform:
_platform
,
processManager:
_processManager
,
terminal:
_terminal
,
).
analyze
();
}
else
{
await
AnalyzeOnce
(
...
...
@@ -94,6 +125,13 @@ class AnalyzeCommand extends FlutterCommand {
runner
.
getRepoRoots
(),
runner
.
getRepoPackages
(),
workingDirectory:
workingDirectory
,
fileSystem:
_fileSystem
,
// TODO(jonahwilliams): determine a better way to inject the logger,
// since it is constructed on-demand.
logger:
_logger
??
globals
.
logger
,
platform:
_platform
,
processManager:
_processManager
,
terminal:
_terminal
,
).
analyze
();
}
return
FlutterCommandResult
.
success
();
...
...
packages/flutter_tools/lib/src/commands/analyze_base.dart
View file @
d2f889b4
...
...
@@ -5,20 +5,47 @@
import
'dart:async'
;
import
'package:args/args.dart'
;
import
'package:meta/meta.dart'
;
import
'package:platform/platform.dart'
;
import
'package:process/process.dart'
;
import
'package:yaml/yaml.dart'
as
yaml
;
import
'../base/common.dart'
;
import
'../base/file_system.dart'
;
import
'../base/logger.dart'
;
import
'../base/terminal.dart'
;
import
'../base/utils.dart'
;
import
'../cache.dart'
;
import
'../globals.dart'
as
globals
;
/// Common behavior for `flutter analyze` and `flutter analyze --watch`
abstract
class
AnalyzeBase
{
AnalyzeBase
(
this
.
argResults
);
AnalyzeBase
(
this
.
argResults
,
{
@required
this
.
repoRoots
,
@required
this
.
repoPackages
,
@required
this
.
fileSystem
,
@required
this
.
logger
,
@required
this
.
platform
,
@required
this
.
processManager
,
@required
this
.
terminal
,
});
/// The parsed argument results for execution.
final
ArgResults
argResults
;
@protected
final
List
<
String
>
repoRoots
;
@protected
final
List
<
Directory
>
repoPackages
;
@protected
final
FileSystem
fileSystem
;
@protected
final
Logger
logger
;
@protected
final
ProcessManager
processManager
;
@protected
final
Platform
platform
;
@protected
final
AnsiTerminal
terminal
;
/// Called by [AnalyzeCommand] to start the analysis process.
Future
<
void
>
analyze
();
...
...
@@ -26,7 +53,7 @@ abstract class AnalyzeBase {
void
dumpErrors
(
Iterable
<
String
>
errors
)
{
if
(
argResults
[
'write'
]
!=
null
)
{
try
{
final
RandomAccessFile
resultsFile
=
globals
.
fs
.
file
(
argResults
[
'write'
]).
openSync
(
mode:
FileMode
.
write
);
final
RandomAccessFile
resultsFile
=
fileSystem
.
file
(
argResults
[
'write'
]).
openSync
(
mode:
FileMode
.
write
);
try
{
resultsFile
.
lockSync
();
resultsFile
.
writeStringSync
(
errors
.
join
(
'
\n
'
));
...
...
@@ -34,7 +61,7 @@ abstract class AnalyzeBase {
resultsFile
.
close
();
}
}
catch
(
e
)
{
globals
.
printError
(
'Failed to save output to "
${argResults['write']}
":
$e
'
);
logger
.
printError
(
'Failed to save output to "
${argResults['write']}
":
$e
'
);
}
}
}
...
...
@@ -46,30 +73,13 @@ abstract class AnalyzeBase {
'issues'
:
errorCount
,
'missingDartDocs'
:
membersMissingDocumentation
,
};
globals
.
fs
.
file
(
benchmarkOut
).
writeAsStringSync
(
toPrettyJson
(
data
));
globals
.
printStatus
(
'Analysis benchmark written to
$benchmarkOut
(
$data
).'
);
fileSystem
.
file
(
benchmarkOut
).
writeAsStringSync
(
toPrettyJson
(
data
));
logger
.
printStatus
(
'Analysis benchmark written to
$benchmarkOut
(
$data
).'
);
}
bool
get
isBenchmarking
=>
argResults
[
'benchmark'
]
as
bool
;
}
/// Return true if [fileList] contains a path that resides inside the Flutter repository.
/// If [fileList] is empty, then return true if the current directory resides inside the Flutter repository.
bool
inRepo
(
List
<
String
>
fileList
)
{
if
(
fileList
==
null
||
fileList
.
isEmpty
)
{
fileList
=
<
String
>[
globals
.
fs
.
path
.
current
];
}
final
String
root
=
globals
.
fs
.
path
.
normalize
(
globals
.
fs
.
path
.
absolute
(
Cache
.
flutterRoot
));
final
String
prefix
=
root
+
globals
.
fs
.
path
.
separator
;
for
(
String
file
in
fileList
)
{
file
=
globals
.
fs
.
path
.
normalize
(
globals
.
fs
.
path
.
absolute
(
file
));
if
(
file
==
root
||
file
.
startsWith
(
prefix
))
{
return
true
;
}
}
return
false
;
}
class
PackageDependency
{
// This is a map from dependency targets (lib directories) to a list
// of places that ask for that target (.packages or pubspec.yaml files)
...
...
packages/flutter_tools/lib/src/commands/analyze_continuously.dart
View file @
d2f889b4
...
...
@@ -5,23 +5,38 @@
import
'dart:async'
;
import
'package:args/args.dart'
;
import
'package:meta/meta.dart'
;
import
'package:platform/platform.dart'
;
import
'package:process/process.dart'
;
import
'../base/common.dart'
;
import
'../base/file_system.dart'
;
import
'../base/io.dart'
;
import
'../base/logger.dart'
;
import
'../base/terminal.dart'
;
import
'../base/utils.dart'
;
import
'../cache.dart'
;
import
'../dart/analysis.dart'
;
import
'../dart/sdk.dart'
as
sdk
;
import
'../globals.dart'
as
globals
;
import
'analyze_base.dart'
;
class
AnalyzeContinuously
extends
AnalyzeBase
{
AnalyzeContinuously
(
ArgResults
argResults
,
this
.
repoRoots
,
this
.
repoPackages
)
:
super
(
argResults
);
final
List
<
String
>
repoRoots
;
final
List
<
Directory
>
repoPackages
;
AnalyzeContinuously
(
ArgResults
argResults
,
List
<
String
>
repoRoots
,
List
<
Directory
>
repoPackages
,
{
@required
FileSystem
fileSystem
,
@required
Logger
logger
,
@required
AnsiTerminal
terminal
,
@required
Platform
platform
,
@required
ProcessManager
processManager
,
})
:
super
(
argResults
,
repoPackages:
repoPackages
,
repoRoots:
repoRoots
,
fileSystem:
fileSystem
,
logger:
logger
,
platform:
platform
,
terminal:
terminal
,
processManager:
processManager
,
);
String
analysisTarget
;
bool
firstAnalysis
=
true
;
...
...
@@ -42,18 +57,24 @@ class AnalyzeContinuously extends AnalyzeBase {
directories
=
repoRoots
;
analysisTarget
=
'Flutter repository'
;
globals
.
printTrace
(
'Analyzing Flutter repository:'
);
logger
.
printTrace
(
'Analyzing Flutter repository:'
);
for
(
final
String
projectPath
in
repoRoots
)
{
globals
.
printTrace
(
'
${globals.fs
.path.relative(projectPath)}
'
);
logger
.
printTrace
(
'
${fileSystem
.path.relative(projectPath)}
'
);
}
}
else
{
directories
=
<
String
>[
globals
.
fs
.
currentDirectory
.
path
];
analysisTarget
=
globals
.
fs
.
currentDirectory
.
path
;
directories
=
<
String
>[
fileSystem
.
currentDirectory
.
path
];
analysisTarget
=
fileSystem
.
currentDirectory
.
path
;
}
final
String
sdkPath
=
argResults
[
'dart-sdk'
]
as
String
??
sdk
.
dartSdkPath
;
final
AnalysisServer
server
=
AnalysisServer
(
sdkPath
,
directories
);
final
AnalysisServer
server
=
AnalysisServer
(
sdkPath
,
directories
,
fileSystem:
fileSystem
,
logger:
logger
,
platform:
platform
,
processManager:
processManager
,
terminal:
terminal
,
);
server
.
onAnalyzing
.
listen
((
bool
isAnalyzing
)
=>
_handleAnalysisStatus
(
server
,
isAnalyzing
));
server
.
onErrors
.
listen
(
_handleAnalysisErrors
);
...
...
@@ -66,7 +87,7 @@ class AnalyzeContinuously extends AnalyzeBase {
if
(
exitCode
!=
0
)
{
throwToolExit
(
message
,
exitCode:
exitCode
);
}
globals
.
printStatus
(
message
);
logger
.
printStatus
(
message
);
if
(
server
.
didServerErrorOccur
)
{
throwToolExit
(
'Server error(s) occurred.'
);
...
...
@@ -77,9 +98,9 @@ class AnalyzeContinuously extends AnalyzeBase {
if
(
isAnalyzing
)
{
analysisStatus
?.
cancel
();
if
(!
firstAnalysis
)
{
globals
.
printStatus
(
'
\n
'
);
logger
.
printStatus
(
'
\n
'
);
}
analysisStatus
=
globals
.
logger
.
startProgress
(
'Analyzing
$analysisTarget
...'
,
timeout:
timeoutConfiguration
.
slowOperation
);
analysisStatus
=
logger
.
startProgress
(
'Analyzing
$analysisTarget
...'
,
timeout:
timeoutConfiguration
.
slowOperation
);
analyzedPaths
.
clear
();
analysisTimer
=
Stopwatch
()..
start
();
}
else
{
...
...
@@ -87,12 +108,12 @@ class AnalyzeContinuously extends AnalyzeBase {
analysisStatus
=
null
;
analysisTimer
.
stop
();
globals
.
logger
.
printStatus
(
globals
.
terminal
.
clearScreen
(),
newline:
false
);
logger
.
printStatus
(
terminal
.
clearScreen
(),
newline:
false
);
// Remove errors for deleted files, sort, and print errors.
final
List
<
AnalysisError
>
errors
=
<
AnalysisError
>[];
for
(
final
String
path
in
analysisErrors
.
keys
.
toList
())
{
if
(
globals
.
fs
.
isFileSync
(
path
))
{
if
(
fileSystem
.
isFileSync
(
path
))
{
errors
.
addAll
(
analysisErrors
[
path
]);
}
else
{
analysisErrors
.
remove
(
path
);
...
...
@@ -113,9 +134,9 @@ class AnalyzeContinuously extends AnalyzeBase {
errors
.
sort
();
for
(
final
AnalysisError
error
in
errors
)
{
globals
.
printStatus
(
error
.
toString
());
logger
.
printStatus
(
error
.
toString
());
if
(
error
.
code
!=
null
)
{
globals
.
printTrace
(
'error code:
${error.code}
'
);
logger
.
printTrace
(
'error code:
${error.code}
'
);
}
}
...
...
@@ -148,9 +169,9 @@ class AnalyzeContinuously extends AnalyzeBase {
final
String
files
=
'
${analyzedPaths.length}
${pluralize('file', analyzedPaths.length)}
'
;
final
String
seconds
=
(
analysisTimer
.
elapsedMilliseconds
/
1000.0
).
toStringAsFixed
(
2
);
if
(
undocumentedMembers
>
0
)
{
globals
.
printStatus
(
'
$errorsMessage
•
$dartdocMessage
• analyzed
$files
in
$seconds
seconds'
);
logger
.
printStatus
(
'
$errorsMessage
•
$dartdocMessage
• analyzed
$files
in
$seconds
seconds'
);
}
else
{
globals
.
printStatus
(
'
$errorsMessage
• analyzed
$files
in
$seconds
seconds'
);
logger
.
printStatus
(
'
$errorsMessage
• analyzed
$files
in
$seconds
seconds'
);
}
if
(
firstAnalysis
&&
isBenchmarking
)
{
...
...
packages/flutter_tools/lib/src/commands/analyze_once.dart
View file @
d2f889b4
...
...
@@ -5,15 +5,18 @@
import
'dart:async'
;
import
'package:args/args.dart'
;
import
'package:meta/meta.dart'
;
import
'package:platform/platform.dart'
;
import
'package:process/process.dart'
;
import
'../base/common.dart'
;
import
'../base/file_system.dart'
;
import
'../base/logger.dart'
;
import
'../base/terminal.dart'
;
import
'../base/utils.dart'
;
import
'../cache.dart'
;
import
'../dart/analysis.dart'
;
import
'../dart/sdk.dart'
as
sdk
;
import
'../globals.dart'
as
globals
;
import
'analyze.dart'
;
import
'analyze_base.dart'
;
...
...
@@ -21,13 +24,24 @@ import 'analyze_base.dart';
class
AnalyzeOnce
extends
AnalyzeBase
{
AnalyzeOnce
(
ArgResults
argResults
,
this
.
repoRoots
,
this
.
repoPackages
,
{
List
<
String
>
repoRoots
,
List
<
Directory
>
repoPackages
,
{
@required
FileSystem
fileSystem
,
@required
Logger
logger
,
@required
Platform
platform
,
@required
ProcessManager
processManager
,
@required
AnsiTerminal
terminal
,
this
.
workingDirectory
,
})
:
super
(
argResults
);
final
List
<
String
>
repoRoots
;
final
List
<
Directory
>
repoPackages
;
})
:
super
(
argResults
,
repoRoots:
repoRoots
,
repoPackages:
repoPackages
,
fileSystem:
fileSystem
,
logger:
logger
,
platform:
platform
,
processManager:
processManager
,
terminal:
terminal
,
);
/// The working directory for testing analysis using dartanalyzer.
final
Directory
workingDirectory
;
...
...
@@ -35,14 +49,14 @@ class AnalyzeOnce extends AnalyzeBase {
@override
Future
<
void
>
analyze
()
async
{
final
String
currentDirectory
=
(
workingDirectory
??
globals
.
fs
.
currentDirectory
).
path
;
(
workingDirectory
??
fileSystem
.
currentDirectory
).
path
;
// find directories from argResults.rest
final
Set
<
String
>
directories
=
Set
<
String
>.
from
(
argResults
.
rest
.
map
<
String
>((
String
path
)
=>
globals
.
fs
.
path
.
canonicalize
(
path
)));
.
map
<
String
>((
String
path
)
=>
fileSystem
.
path
.
canonicalize
(
path
)));
if
(
directories
.
isNotEmpty
)
{
for
(
final
String
directory
in
directories
)
{
final
FileSystemEntityType
type
=
globals
.
fs
.
typeSync
(
directory
);
final
FileSystemEntityType
type
=
fileSystem
.
typeSync
(
directory
);
if
(
type
==
FileSystemEntityType
.
notFound
)
{
throwToolExit
(
"'
$directory
' does not exist"
);
...
...
@@ -79,6 +93,11 @@ class AnalyzeOnce extends AnalyzeBase {
final
AnalysisServer
server
=
AnalysisServer
(
sdkPath
,
directories
.
toList
(),
fileSystem:
fileSystem
,
platform:
platform
,
logger:
logger
,
processManager:
processManager
,
terminal:
terminal
,
);
StreamSubscription
<
bool
>
subscription
;
...
...
@@ -108,9 +127,9 @@ class AnalyzeOnce extends AnalyzeBase {
final
Stopwatch
timer
=
Stopwatch
()..
start
();
final
String
message
=
directories
.
length
>
1
?
'
${directories.length}
${directories.length == 1 ? 'directory' : 'directories'}
'
:
globals
.
fs
.
path
.
basename
(
directories
.
first
);
:
fileSystem
.
path
.
basename
(
directories
.
first
);
final
Status
progress
=
argResults
[
'preamble'
]
as
bool
?
globals
.
logger
.
startProgress
(
'Analyzing
$message
...'
,
timeout:
timeoutConfiguration
.
slowOperation
)
?
logger
.
startProgress
(
'Analyzing
$message
...'
,
timeout:
timeoutConfiguration
.
slowOperation
)
:
null
;
await
analysisCompleter
.
future
;
...
...
@@ -135,11 +154,11 @@ class AnalyzeOnce extends AnalyzeBase {
// report errors
if
(
errors
.
isNotEmpty
&&
(
argResults
[
'preamble'
]
as
bool
))
{
globals
.
printStatus
(
''
);
logger
.
printStatus
(
''
);
}
errors
.
sort
();
for
(
final
AnalysisError
error
in
errors
)
{
globals
.
printStatus
(
error
.
toString
(),
hangingIndent:
7
);
logger
.
printStatus
(
error
.
toString
(),
hangingIndent:
7
);
}
final
String
seconds
=
(
timer
.
elapsedMilliseconds
/
1000.0
).
toStringAsFixed
(
1
);
...
...
@@ -154,7 +173,7 @@ class AnalyzeOnce extends AnalyzeBase {
// We consider any level of error to be an error exit (we don't report different levels).
if
(
errors
.
isNotEmpty
)
{
final
int
errorCount
=
errors
.
length
;
globals
.
printStatus
(
''
);
logger
.
printStatus
(
''
);
if
(
undocumentedMembers
>
0
)
{
throwToolExit
(
'
$errorCount
${pluralize('issue', errorCount)}
found. (ran in
${seconds}
s;
$dartdocMessage
)'
);
}
else
{
...
...
@@ -168,9 +187,9 @@ class AnalyzeOnce extends AnalyzeBase {
if
(
argResults
[
'congratulate'
]
as
bool
)
{
if
(
undocumentedMembers
>
0
)
{
globals
.
printStatus
(
'No issues found! (ran in
${seconds}
s;
$dartdocMessage
)'
);
logger
.
printStatus
(
'No issues found! (ran in
${seconds}
s;
$dartdocMessage
)'
);
}
else
{
globals
.
printStatus
(
'No issues found! (ran in
${seconds}
s)'
);
logger
.
printStatus
(
'No issues found! (ran in
${seconds}
s)'
);
}
}
}
...
...
packages/flutter_tools/lib/src/dart/analysis.dart
View file @
d2f889b4
...
...
@@ -5,18 +5,39 @@
import
'dart:async'
;
import
'dart:math'
as
math
;
import
'package:meta/meta.dart'
;
import
'package:platform/platform.dart'
;
import
'package:process/process.dart'
;
import
'../base/common.dart'
;
import
'../base/file_system.dart'
;
import
'../base/io.dart'
;
import
'../base/logger.dart'
;
import
'../base/terminal.dart'
;
import
'../base/utils.dart'
;
import
'../convert.dart'
;
import
'../globals.dart'
as
globals
;
/// An interface to the Dart analysis server.
class
AnalysisServer
{
AnalysisServer
(
this
.
sdkPath
,
this
.
directories
);
AnalysisServer
(
this
.
sdkPath
,
this
.
directories
,
{
@required
FileSystem
fileSystem
,
@required
ProcessManager
processManager
,
@required
Logger
logger
,
@required
Platform
platform
,
@required
AnsiTerminal
terminal
,
})
:
_fileSystem
=
fileSystem
,
_processManager
=
processManager
,
_logger
=
logger
,
_platform
=
platform
,
_terminal
=
terminal
;
final
String
sdkPath
;
final
List
<
String
>
directories
;
final
FileSystem
_fileSystem
;
final
ProcessManager
_processManager
;
final
Logger
_logger
;
final
Platform
_platform
;
final
AnsiTerminal
_terminal
;
Process
_process
;
final
StreamController
<
bool
>
_analyzingController
=
...
...
@@ -29,9 +50,9 @@ class AnalysisServer {
Future
<
void
>
start
()
async
{
final
String
snapshot
=
globals
.
fs
.
path
.
join
(
sdkPath
,
'bin/snapshots/analysis_server.dart.snapshot'
);
_fileSystem
.
path
.
join
(
sdkPath
,
'bin/snapshots/analysis_server.dart.snapshot'
);
final
List
<
String
>
command
=
<
String
>[
globals
.
fs
.
path
.
join
(
sdkPath
,
'bin'
,
'dart'
),
_fileSystem
.
path
.
join
(
sdkPath
,
'bin'
,
'dart'
),
snapshot
,
'--disable-server-feature-completion'
,
'--disable-server-feature-search'
,
...
...
@@ -39,14 +60,14 @@ class AnalysisServer {
sdkPath
,
];
globals
.
printTrace
(
'dart
${command.skip(1).join(' ')}
'
);
_process
=
await
globals
.
processManager
.
start
(
command
);
_logger
.
printTrace
(
'dart
${command.skip(1).join(' ')}
'
);
_process
=
await
_
processManager
.
start
(
command
);
// This callback hookup can't throw.
unawaited
(
_process
.
exitCode
.
whenComplete
(()
=>
_process
=
null
));
final
Stream
<
String
>
errorStream
=
_process
.
stderr
.
transform
<
String
>(
utf8
.
decoder
).
transform
<
String
>(
const
LineSplitter
());
errorStream
.
listen
(
globals
.
printError
);
errorStream
.
listen
(
_logger
.
printError
);
final
Stream
<
String
>
inStream
=
_process
.
stdout
.
transform
<
String
>(
utf8
.
decoder
).
transform
<
String
>(
const
LineSplitter
());
...
...
@@ -73,11 +94,11 @@ class AnalysisServer {
'params'
:
params
,
});
_process
.
stdin
.
writeln
(
message
);
globals
.
printTrace
(
'==>
$message
'
);
_logger
.
printTrace
(
'==>
$message
'
);
}
void
_handleServerResponse
(
String
line
)
{
globals
.
printTrace
(
'<==
$line
'
);
_logger
.
printTrace
(
'<==
$line
'
);
final
dynamic
response
=
json
.
decode
(
line
);
...
...
@@ -98,10 +119,10 @@ class AnalysisServer {
}
else
if
(
response
[
'error'
]
!=
null
)
{
// Fields are 'code', 'message', and 'stackTrace'.
final
Map
<
String
,
dynamic
>
error
=
castStringKeyedMap
(
response
[
'error'
]);
globals
.
printError
(
_logger
.
printError
(
'Error response from the server:
${error['code']}
${error['message']}
'
);
if
(
error
[
'stackTrace'
]
!=
null
)
{
globals
.
printError
(
error
[
'stackTrace'
]
as
String
);
_logger
.
printError
(
error
[
'stackTrace'
]
as
String
);
}
}
}
...
...
@@ -117,9 +138,9 @@ class AnalysisServer {
void
_handleServerError
(
Map
<
String
,
dynamic
>
error
)
{
// Fields are 'isFatal', 'message', and 'stackTrace'.
globals
.
printError
(
'Error from the analysis server:
${error['message']}
'
);
_logger
.
printError
(
'Error from the analysis server:
${error['message']}
'
);
if
(
error
[
'stackTrace'
]
!=
null
)
{
globals
.
printError
(
error
[
'stackTrace'
]
as
String
);
_logger
.
printError
(
error
[
'stackTrace'
]
as
String
);
}
_didServerErrorOccur
=
true
;
}
...
...
@@ -130,7 +151,13 @@ class AnalysisServer {
final
List
<
dynamic
>
errorsList
=
issueInfo
[
'errors'
]
as
List
<
dynamic
>;
final
List
<
AnalysisError
>
errors
=
errorsList
.
map
<
Map
<
String
,
dynamic
>>(
castStringKeyedMap
)
.
map
<
AnalysisError
>((
Map
<
String
,
dynamic
>
json
)
=>
AnalysisError
(
json
))
.
map
<
AnalysisError
>((
Map
<
String
,
dynamic
>
json
)
{
return
AnalysisError
(
json
,
fileSystem:
_fileSystem
,
platform:
_platform
,
terminal:
_terminal
,
);
})
.
toList
();
if
(!
_errorsController
.
isClosed
)
{
_errorsController
.
add
(
FileAnalysisErrors
(
file
,
errors
));
...
...
@@ -152,7 +179,17 @@ enum _AnalysisSeverity {
}
class
AnalysisError
implements
Comparable
<
AnalysisError
>
{
AnalysisError
(
this
.
json
);
AnalysisError
(
this
.
json
,
{
@required
Platform
platform
,
@required
AnsiTerminal
terminal
,
@required
FileSystem
fileSystem
,
})
:
_platform
=
platform
,
_terminal
=
terminal
,
_fileSystem
=
fileSystem
;
final
Platform
_platform
;
final
AnsiTerminal
_terminal
;
final
FileSystem
_fileSystem
;
static
final
Map
<
String
,
_AnalysisSeverity
>
_severityMap
=
<
String
,
_AnalysisSeverity
>{
'INFO'
:
_AnalysisSeverity
.
info
,
...
...
@@ -160,7 +197,7 @@ class AnalysisError implements Comparable<AnalysisError> {
'ERROR'
:
_AnalysisSeverity
.
error
,
};
static
final
String
_separator
=
globals
.
platform
.
isWindows
?
'-'
:
'•'
;
String
get
_separator
=>
_
platform
.
isWindows
?
'-'
:
'•'
;
// "severity":"INFO","type":"TODO","location":{
// "file":"/Users/.../lib/test.dart","offset":362,"length":72,"startLine":15,"startColumn":4
...
...
@@ -171,9 +208,9 @@ class AnalysisError implements Comparable<AnalysisError> {
String
get
colorSeverity
{
switch
(
_severityLevel
)
{
case
_AnalysisSeverity
.
error
:
return
globals
.
terminal
.
color
(
severity
,
TerminalColor
.
red
);
return
_
terminal
.
color
(
severity
,
TerminalColor
.
red
);
case
_AnalysisSeverity
.
warning
:
return
globals
.
terminal
.
color
(
severity
,
TerminalColor
.
yellow
);
return
_
terminal
.
color
(
severity
,
TerminalColor
.
yellow
);
case
_AnalysisSeverity
.
info
:
case
_AnalysisSeverity
.
none
:
return
severity
;
...
...
@@ -224,7 +261,7 @@ class AnalysisError implements Comparable<AnalysisError> {
final
String
padding
=
' '
*
math
.
max
(
0
,
7
-
severity
.
length
);
return
'
$padding${colorSeverity.toLowerCase()}
$_separator
'
'
$messageSentenceFragment
$_separator
'
'
${
globals.fs
.path.relative(file)}
:
$startLine
:
$startColumn
$_separator
'
'
${
_fileSystem
.path.relative(file)}
:
$startLine
:
$startColumn
$_separator
'
'
$code
'
;
}
...
...
packages/flutter_tools/test/commands.shard/hermetic/analyze_continuously_test.dart
View file @
d2f889b4
...
...
@@ -5,12 +5,15 @@
import
'dart:async'
;
import
'package:flutter_tools/src/base/file_system.dart'
;
import
'package:flutter_tools/src/base/os.dart'
;
import
'package:flutter_tools/src/base/io.dart'
;
import
'package:flutter_tools/src/base/logger.dart'
;
import
'package:flutter_tools/src/base/terminal.dart'
;
import
'package:flutter_tools/src/dart/analysis.dart'
;
import
'package:flutter_tools/src/dart/pub.dart'
;
import
'package:flutter_tools/src/dart/sdk.dart'
;
import
'package:flutter_tools/src/runner/flutter_command_runner.dart'
;
import
'package:flutter_tools/src/globals.dart'
as
globals
;
import
'package:platform/platform.dart'
;
import
'package:process/process.dart'
;
import
'../../src/common.dart'
;
import
'../../src/context.dart'
;
...
...
@@ -18,10 +21,21 @@ import '../../src/context.dart';
void
main
(
)
{
AnalysisServer
server
;
Directory
tempDir
;
FileSystem
fileSystem
;
Platform
platform
;
ProcessManager
processManager
;
AnsiTerminal
terminal
;
Logger
logger
;
setUp
(()
{
platform
=
const
LocalPlatform
();
fileSystem
=
const
LocalFileSystem
();
platform
=
const
LocalPlatform
();
processManager
=
const
LocalProcessManager
();
terminal
=
AnsiTerminal
(
platform:
platform
,
stdio:
Stdio
());
logger
=
BufferLogger
(
outputPreferences:
OutputPreferences
.
test
(),
terminal:
terminal
);
FlutterCommandRunner
.
initFlutterRoot
();
tempDir
=
globals
.
fs
.
systemTempDirectory
.
createTempSync
(
'flutter_analysis_test.'
);
tempDir
=
fileSystem
.
systemTempDirectory
.
createTempSync
(
'flutter_analysis_test.'
);
});
tearDown
(()
{
...
...
@@ -29,13 +43,36 @@ void main() {
return
server
?.
dispose
();
});
void
_createSampleProject
(
Directory
directory
,
{
bool
brokenCode
=
false
})
{
final
File
pubspecFile
=
fileSystem
.
file
(
fileSystem
.
path
.
join
(
directory
.
path
,
'pubspec.yaml'
));
pubspecFile
.
writeAsStringSync
(
'''
name: foo_project
'''
);
final
File
dartFile
=
fileSystem
.
file
(
fileSystem
.
path
.
join
(
directory
.
path
,
'lib'
,
'main.dart'
));
dartFile
.
parent
.
createSync
();
dartFile
.
writeAsStringSync
(
'''
void main() {
print('
hello
world
');
${brokenCode ? 'prints("hello world");' : ''}
}
'''
);
}
group
(
'analyze --watch'
,
()
{
testUsingContext
(
'AnalysisServer success'
,
()
async
{
_createSampleProject
(
tempDir
);
await
pub
.
get
(
context:
PubContext
.
flutterTests
,
directory:
tempDir
.
path
);
await
const
Pub
()
.
get
(
context:
PubContext
.
flutterTests
,
directory:
tempDir
.
path
);
server
=
AnalysisServer
(
dartSdkPath
,
<
String
>[
tempDir
.
path
]);
server
=
AnalysisServer
(
dartSdkPath
,
<
String
>[
tempDir
.
path
],
fileSystem:
fileSystem
,
platform:
platform
,
processManager:
processManager
,
logger:
logger
,
terminal:
terminal
,
);
int
errorCount
=
0
;
final
Future
<
bool
>
onDone
=
server
.
onAnalyzing
.
where
((
bool
analyzing
)
=>
analyzing
==
false
).
first
;
...
...
@@ -45,18 +82,21 @@ void main() {
await
onDone
;
expect
(
errorCount
,
0
);
},
overrides:
<
Type
,
Generator
>{
OperatingSystemUtils:
()
=>
globals
.
os
,
Pub:
()
=>
const
Pub
(),
});
});
testUsingContext
(
'AnalysisServer errors'
,
()
async
{
_createSampleProject
(
tempDir
,
brokenCode:
true
);
await
pub
.
get
(
context:
PubContext
.
flutterTests
,
directory:
tempDir
.
path
);
await
const
Pub
()
.
get
(
context:
PubContext
.
flutterTests
,
directory:
tempDir
.
path
);
server
=
AnalysisServer
(
dartSdkPath
,
<
String
>[
tempDir
.
path
]);
server
=
AnalysisServer
(
dartSdkPath
,
<
String
>[
tempDir
.
path
],
fileSystem:
fileSystem
,
platform:
platform
,
processManager:
processManager
,
logger:
logger
,
terminal:
terminal
,
);
int
errorCount
=
0
;
final
Future
<
bool
>
onDone
=
server
.
onAnalyzing
.
where
((
bool
analyzing
)
=>
analyzing
==
false
).
first
;
...
...
@@ -68,15 +108,18 @@ void main() {
await
onDone
;
expect
(
errorCount
,
greaterThan
(
0
));
},
overrides:
<
Type
,
Generator
>{
OperatingSystemUtils:
()
=>
globals
.
os
,
Pub:
()
=>
const
Pub
(),
});
testUsingContext
(
'Returns no errors when source is error-free'
,
()
async
{
const
String
contents
=
"StringBuffer bar = StringBuffer('baz');"
;
tempDir
.
childFile
(
'main.dart'
).
writeAsStringSync
(
contents
);
server
=
AnalysisServer
(
dartSdkPath
,
<
String
>[
tempDir
.
path
]);
server
=
AnalysisServer
(
dartSdkPath
,
<
String
>[
tempDir
.
path
],
fileSystem:
fileSystem
,
platform:
platform
,
processManager:
processManager
,
logger:
logger
,
terminal:
terminal
,
);
int
errorCount
=
0
;
final
Future
<
bool
>
onDone
=
server
.
onAnalyzing
.
where
((
bool
analyzing
)
=>
analyzing
==
false
).
first
;
...
...
@@ -86,24 +129,5 @@ void main() {
await
server
.
start
();
await
onDone
;
expect
(
errorCount
,
0
);
},
overrides:
<
Type
,
Generator
>{
OperatingSystemUtils:
()
=>
globals
.
os
,
Pub:
()
=>
const
Pub
(),
});
}
void
_createSampleProject
(
Directory
directory
,
{
bool
brokenCode
=
false
})
{
final
File
pubspecFile
=
globals
.
fs
.
file
(
globals
.
fs
.
path
.
join
(
directory
.
path
,
'pubspec.yaml'
));
pubspecFile
.
writeAsStringSync
(
'''
name: foo_project
'''
);
final
File
dartFile
=
globals
.
fs
.
file
(
globals
.
fs
.
path
.
join
(
directory
.
path
,
'lib'
,
'main.dart'
));
dartFile
.
parent
.
createSync
();
dartFile
.
writeAsStringSync
(
'''
void main() {
print('
hello
world
');
${brokenCode ? 'prints("hello world");' : ''}
}
'''
);
}
packages/flutter_tools/test/commands.shard/hermetic/analyze_test.dart
View file @
d2f889b4
...
...
@@ -5,7 +5,6 @@
import
'package:file/file.dart'
;
import
'package:file/memory.dart'
;
import
'package:flutter_tools/src/cache.dart'
;
import
'package:flutter_tools/src/commands/analyze_base.dart'
;
import
'package:flutter_tools/src/globals.dart'
as
globals
;
import
'../../src/common.dart'
;
...
...
@@ -13,6 +12,23 @@ import '../../src/context.dart';
const
String
_kFlutterRoot
=
'/data/flutter'
;
/// Return true if [fileList] contains a path that resides inside the Flutter repository.
/// If [fileList] is empty, then return true if the current directory resides inside the Flutter repository.
bool
inRepo
(
List
<
String
>
fileList
)
{
if
(
fileList
==
null
||
fileList
.
isEmpty
)
{
fileList
=
<
String
>[
globals
.
fs
.
path
.
current
];
}
final
String
root
=
globals
.
fs
.
path
.
normalize
(
globals
.
fs
.
path
.
absolute
(
Cache
.
flutterRoot
));
final
String
prefix
=
root
+
globals
.
fs
.
path
.
separator
;
for
(
String
file
in
fileList
)
{
file
=
globals
.
fs
.
path
.
normalize
(
globals
.
fs
.
path
.
absolute
(
file
));
if
(
file
==
root
||
file
.
startsWith
(
prefix
))
{
return
true
;
}
}
return
false
;
}
void
main
(
)
{
FileSystem
fs
;
Directory
tempDir
;
...
...
packages/flutter_tools/test/commands.shard/permeable/analyze_once_test.dart
View file @
d2f889b4
This diff is collapsed.
Click to expand it.
packages/flutter_tools/test/general.shard/dart/sdk_validation_test.dart
deleted
100644 → 0
View file @
bafa03e5
// Copyright 2014 The Flutter Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
import
'dart:async'
;
import
'package:flutter_tools/src/base/file_system.dart'
;
import
'package:flutter_tools/src/cache.dart'
;
import
'package:flutter_tools/src/dart/analysis.dart'
;
import
'package:flutter_tools/src/dart/pub.dart'
;
import
'package:flutter_tools/src/dart/sdk.dart'
;
import
'package:flutter_tools/src/globals.dart'
as
globals
;
import
'../../src/common.dart'
;
import
'../../src/context.dart'
;
void
main
(
)
{
testSampleProject
(
'ui'
,
'Window'
);
testSampleProject
(
'html'
,
'HttpStatus'
);
testSampleProject
(
'js'
,
'allowInterop'
);
testSampleProject
(
'js_util'
,
'jsify'
);
}
void
testSampleProject
(
String
lib
,
String
member
)
{
testUsingContext
(
'contains dart:
$lib
'
,
()
async
{
Cache
.
disableLocking
();
final
Directory
projectDirectory
=
globals
.
fs
.
systemTempDirectory
.
createTempSync
(
'flutter_sdk_validation_
${lib}
_test.'
).
absolute
;
try
{
final
File
pubspecFile
=
globals
.
fs
.
file
(
globals
.
fs
.
path
.
join
(
projectDirectory
.
path
,
'pubspec.yaml'
));
pubspecFile
.
writeAsStringSync
(
'''
name:
${lib}
_project
dependencies:
flutter:
sdk: flutter
'''
);
final
File
dartFile
=
globals
.
fs
.
file
(
globals
.
fs
.
path
.
join
(
projectDirectory
.
path
,
'lib'
,
'main.dart'
));
dartFile
.
parent
.
createSync
();
dartFile
.
writeAsStringSync
(
'''
import '
dart:
$lib
' as
$lib
;
void main() {
// ignore: unnecessary_statements
$lib
.
$member
;
}
'''
);
await
pub
.
get
(
context:
PubContext
.
flutterTests
,
directory:
projectDirectory
.
path
);
final
AnalysisServer
server
=
AnalysisServer
(
dartSdkPath
,
<
String
>[
projectDirectory
.
path
]);
try
{
final
int
errorCount
=
await
analyze
(
server
);
expect
(
errorCount
,
0
);
}
finally
{
await
server
.
dispose
();
}
}
finally
{
tryToDelete
(
projectDirectory
);
Cache
.
enableLocking
();
}
},
skip:
true
);
}
Future
<
int
>
analyze
(
AnalysisServer
server
)
async
{
int
errorCount
=
0
;
final
Future
<
bool
>
onDone
=
server
.
onAnalyzing
.
where
((
bool
analyzing
)
=>
analyzing
==
false
).
first
;
server
.
onErrors
.
listen
((
FileAnalysisErrors
result
)
{
for
(
final
AnalysisError
error
in
result
.
errors
)
{
print
(
error
.
toString
().
trim
());
}
errorCount
+=
result
.
errors
.
length
;
});
await
server
.
start
();
await
onDone
;
return
errorCount
;
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment