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
ce40fbaf
Unverified
Commit
ce40fbaf
authored
Mar 27, 2020
by
Jenn Magder
Committed by
GitHub
Mar 27, 2020
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Include metadata in GitHub crash template (#53118)
parent
adbc16b6
Changes
8
Show whitespace changes
Inline
Side-by-side
Showing
8 changed files
with
300 additions
and
119 deletions
+300
-119
runner.dart
packages/flutter_tools/lib/runner.dart
+8
-1
create.dart
packages/flutter_tools/lib/src/commands/create.dart
+29
-78
flutter_project_metadata.dart
packages/flutter_tools/lib/src/flutter_project_metadata.dart
+99
-0
globals.dart
packages/flutter_tools/lib/src/globals.dart
+2
-0
project.dart
packages/flutter_tools/lib/src/project.dart
+4
-4
github_template.dart
...ages/flutter_tools/lib/src/reporting/github_template.dart
+26
-14
flutter_project_metadata_test.dart
...ols/test/general.shard/flutter_project_metadata_test.dart
+75
-0
github_template_test.dart
...lutter_tools/test/general.shard/github_template_test.dart
+57
-22
No files found.
packages/flutter_tools/lib/runner.dart
View file @
ce40fbaf
...
...
@@ -14,6 +14,7 @@ import 'src/base/context.dart';
import
'src/base/file_system.dart'
;
import
'src/base/io.dart'
;
import
'src/base/logger.dart'
;
import
'src/base/net.dart'
;
import
'src/base/process.dart'
;
import
'src/context_runner.dart'
;
import
'src/doctor.dart'
;
...
...
@@ -157,7 +158,13 @@ Future<void> _informUserOfCrash(List<String> args, dynamic error, StackTrace sta
globals
.
printError
(
'A crash report has been written to
${file.path}
.'
);
globals
.
printStatus
(
'This crash may already be reported. Check GitHub for similar crashes.'
,
emphasis:
true
);
final
GitHubTemplateCreator
gitHubTemplateCreator
=
context
.
get
<
GitHubTemplateCreator
>()
??
GitHubTemplateCreator
();
final
HttpClientFactory
clientFactory
=
context
.
get
<
HttpClientFactory
>();
final
GitHubTemplateCreator
gitHubTemplateCreator
=
context
.
get
<
GitHubTemplateCreator
>()
??
GitHubTemplateCreator
(
fileSystem:
globals
.
fs
,
logger:
globals
.
logger
,
flutterProjectFactory:
globals
.
projectFactory
,
client:
clientFactory
!=
null
?
clientFactory
()
:
HttpClient
(),
);
final
String
similarIssuesURL
=
await
gitHubTemplateCreator
.
toolCrashSimilarIssuesGitHubURL
(
errorString
);
globals
.
printStatus
(
'
$similarIssuesURL
\n
'
,
wrap:
false
);
globals
.
printStatus
(
'To report your crash to the Flutter team, first read the guide to filing a bug.'
,
emphasis:
true
);
...
...
packages/flutter_tools/lib/src/commands/create.dart
View file @
ce40fbaf
...
...
@@ -5,7 +5,6 @@
import
'dart:async'
;
import
'package:meta/meta.dart'
;
import
'package:yaml/yaml.dart'
as
yaml
;
import
'../android/android.dart'
as
android
;
import
'../android/android_sdk.dart'
as
android_sdk
;
...
...
@@ -21,38 +20,13 @@ import '../convert.dart';
import
'../dart/pub.dart'
;
import
'../doctor.dart'
;
import
'../features.dart'
;
import
'../flutter_project_metadata.dart'
;
import
'../globals.dart'
as
globals
;
import
'../project.dart'
;
import
'../reporting/reporting.dart'
;
import
'../runner/flutter_command.dart'
;
import
'../template.dart'
;
enum
_ProjectType
{
/// This is the default project with the user-managed host code.
/// It is different than the "module" template in that it exposes and doesn't
/// manage the platform code.
app
,
/// The is a project that has managed platform host code. It is an application with
/// ephemeral .ios and .android directories that can be updated automatically.
module
,
/// This is a Flutter Dart package project. It doesn't have any native
/// components, only Dart.
package
,
/// This is a native plugin project.
plugin
,
}
_ProjectType
_stringToProjectType
(
String
value
)
{
_ProjectType
result
;
for
(
final
_ProjectType
type
in
_ProjectType
.
values
)
{
if
(
value
==
getEnumName
(
type
))
{
result
=
type
;
break
;
}
}
return
result
;
}
class
CreateCommand
extends
FlutterCommand
{
CreateCommand
()
{
argParser
.
addFlag
(
'pub'
,
...
...
@@ -74,17 +48,17 @@ class CreateCommand extends FlutterCommand {
argParser
.
addOption
(
'template'
,
abbr:
't'
,
allowed:
_ProjectType
.
values
.
map
<
String
>((
_ProjectType
type
)
=>
getEnumName
(
type
)
),
allowed:
FlutterProjectType
.
values
.
map
<
String
>((
FlutterProjectType
type
)
=>
type
.
name
),
help:
'Specify the type of project to create.'
,
valueHelp:
'type'
,
allowedHelp:
<
String
,
String
>{
getEnumName
(
_ProjectType
.
app
)
:
'(default) Generate a Flutter application.'
,
getEnumName
(
_ProjectType
.
package
)
:
'Generate a shareable Flutter project containing modular '
FlutterProjectType
.
app
.
name
:
'(default) Generate a Flutter application.'
,
FlutterProjectType
.
package
.
name
:
'Generate a shareable Flutter project containing modular '
'Dart code.'
,
getEnumName
(
_ProjectType
.
plugin
)
:
'Generate a shareable Flutter project containing an API '
FlutterProjectType
.
plugin
.
name
:
'Generate a shareable Flutter project containing an API '
'in Dart code with a platform-specific implementation for Android, for iOS code, or '
'for both.'
,
getEnumName
(
_ProjectType
.
module
)
:
'Generate a project to add a Flutter module to an '
FlutterProjectType
.
module
.
name
:
'Generate a project to add a Flutter module to an '
'existing Android or iOS application.'
,
},
defaultsTo:
null
,
...
...
@@ -180,47 +154,24 @@ class CreateCommand extends FlutterCommand {
// If it has an ios dir and an ios/Flutter dir, it's a legacy app
// Otherwise, we don't presume to know what type of project it could be, since
// many of the files could be missing, and we can't really tell definitively.
_ProjectType
_determineTemplateType
(
Directory
projectDir
)
{
yaml
.
YamlMap
loadMetadata
(
Directory
projectDir
)
{
if
(!
projectDir
.
existsSync
())
{
return
null
;
}
FlutterProjectType
_determineTemplateType
(
Directory
projectDir
)
{
final
File
metadataFile
=
globals
.
fs
.
file
(
globals
.
fs
.
path
.
join
(
projectDir
.
absolute
.
path
,
'.metadata'
));
if
(!
metadataFile
.
existsSync
())
{
return
null
;
}
final
dynamic
metadataYaml
=
yaml
.
loadYaml
(
metadataFile
.
readAsStringSync
());
if
(
metadataYaml
is
yaml
.
YamlMap
)
{
return
metadataYaml
;
}
else
{
throwToolExit
(
'pubspec.yaml is malformed.'
);
return
null
;
}
final
FlutterProjectMetadata
projectMetadata
=
FlutterProjectMetadata
(
metadataFile
,
globals
.
logger
);
if
(
projectMetadata
.
projectType
!=
null
)
{
return
projectMetadata
.
projectType
;
}
bool
exists
(
List
<
String
>
path
)
{
return
globals
.
fs
.
directory
(
globals
.
fs
.
path
.
joinAll
(<
String
>[
projectDir
.
absolute
.
path
,
...
path
])).
existsSync
();
}
// If it exists, the project type in the metadata is definitive.
final
yaml
.
YamlMap
metadata
=
loadMetadata
(
projectDir
);
if
(
metadata
!=
null
&&
metadata
[
'project_type'
]
!=
null
)
{
final
dynamic
projectType
=
metadata
[
'project_type'
];
if
(
projectType
is
String
)
{
return
_stringToProjectType
(
projectType
);
}
else
{
throwToolExit
(
'.metadata is malformed.'
);
return
null
;
}
}
// There either wasn't any metadata, or it didn't contain the project type,
// so try and figure out what type of project it is from the existing
// directory structure.
if
(
exists
(<
String
>[
'android'
,
'app'
])
||
exists
(<
String
>[
'ios'
,
'Runner'
])
||
exists
(<
String
>[
'ios'
,
'Flutter'
]))
{
return
_
ProjectType
.
app
;
return
Flutter
ProjectType
.
app
;
}
// Since we can't really be definitive on nearly-empty directories, err on
// the side of prudence and just say we don't know.
...
...
@@ -277,12 +228,12 @@ class CreateCommand extends FlutterCommand {
}
}
_
ProjectType
_getProjectType
(
Directory
projectDir
)
{
_
ProjectType
template
;
_
ProjectType
detectedProjectType
;
Flutter
ProjectType
_getProjectType
(
Directory
projectDir
)
{
Flutter
ProjectType
template
;
Flutter
ProjectType
detectedProjectType
;
final
bool
metadataExists
=
projectDir
.
absolute
.
childFile
(
'.metadata'
).
existsSync
();
if
(
argResults
[
'template'
]
!=
null
)
{
template
=
_
stringToProjectType
(
stringArg
(
'template'
));
template
=
stringToProjectType
(
stringArg
(
'template'
));
}
else
{
// If the project directory exists and isn't empty, then try to determine the template
// type from the project directory.
...
...
@@ -297,12 +248,12 @@ class CreateCommand extends FlutterCommand {
}
}
}
template
??=
detectedProjectType
??
_
ProjectType
.
app
;
template
??=
detectedProjectType
??
Flutter
ProjectType
.
app
;
if
(
detectedProjectType
!=
null
&&
template
!=
detectedProjectType
&&
metadataExists
)
{
// We can only be definitive that this is the wrong type if the .metadata file
// exists and contains a type that doesn't match.
throwToolExit
(
"The requested template type '
${
getEnumName(template)
}
' doesn't match the "
"existing template type of '
${
getEnumName(detectedProjectType)
}
'."
);
throwToolExit
(
"The requested template type '
${
template.name
}
' doesn't match the "
"existing template type of '
${
detectedProjectType.name
}
'."
);
}
return
template
;
}
...
...
@@ -356,18 +307,18 @@ class CreateCommand extends FlutterCommand {
String
sampleCode
;
if
(
argResults
[
'sample'
]
!=
null
)
{
if
(
argResults
[
'template'
]
!=
null
&&
_stringToProjectType
(
stringArg
(
'template'
)
??
'app'
)
!=
_
ProjectType
.
app
)
{
stringToProjectType
(
stringArg
(
'template'
)
??
'app'
)
!=
Flutter
ProjectType
.
app
)
{
throwToolExit
(
'Cannot specify --sample with a project type other than '
'"
${
getEnumName(_ProjectType.app)
}
"'
);
'"
${
FlutterProjectType.app.name
}
"'
);
}
// Fetch the sample from the server.
sampleCode
=
await
_fetchSampleFromServer
(
stringArg
(
'sample'
));
}
final
_
ProjectType
template
=
_getProjectType
(
projectDir
);
final
bool
generateModule
=
template
==
_
ProjectType
.
module
;
final
bool
generatePlugin
=
template
==
_
ProjectType
.
plugin
;
final
bool
generatePackage
=
template
==
_
ProjectType
.
package
;
final
Flutter
ProjectType
template
=
_getProjectType
(
projectDir
);
final
bool
generateModule
=
template
==
Flutter
ProjectType
.
module
;
final
bool
generatePlugin
=
template
==
Flutter
ProjectType
.
plugin
;
final
bool
generatePackage
=
template
==
Flutter
ProjectType
.
package
;
String
organization
=
stringArg
(
'org'
);
if
(!
argResults
.
wasParsed
(
'org'
))
{
...
...
@@ -424,16 +375,16 @@ class CreateCommand extends FlutterCommand {
final
Directory
relativeDir
=
globals
.
fs
.
directory
(
projectDirPath
);
int
generatedFileCount
=
0
;
switch
(
template
)
{
case
_
ProjectType
.
app
:
case
Flutter
ProjectType
.
app
:
generatedFileCount
+=
await
_generateApp
(
relativeDir
,
templateContext
,
overwrite:
overwrite
);
break
;
case
_
ProjectType
.
module
:
case
Flutter
ProjectType
.
module
:
generatedFileCount
+=
await
_generateModule
(
relativeDir
,
templateContext
,
overwrite:
overwrite
);
break
;
case
_
ProjectType
.
package
:
case
Flutter
ProjectType
.
package
:
generatedFileCount
+=
await
_generatePackage
(
relativeDir
,
templateContext
,
overwrite:
overwrite
);
break
;
case
_
ProjectType
.
plugin
:
case
Flutter
ProjectType
.
plugin
:
generatedFileCount
+=
await
_generatePlugin
(
relativeDir
,
templateContext
,
overwrite:
overwrite
);
break
;
}
...
...
packages/flutter_tools/lib/src/flutter_project_metadata.dart
0 → 100644
View file @
ce40fbaf
// 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
'package:yaml/yaml.dart'
;
import
'base/file_system.dart'
;
import
'base/logger.dart'
;
import
'base/utils.dart'
;
enum
FlutterProjectType
{
/// This is the default project with the user-managed host code.
/// It is different than the "module" template in that it exposes and doesn't
/// manage the platform code.
app
,
/// The is a project that has managed platform host code. It is an application with
/// ephemeral .ios and .android directories that can be updated automatically.
module
,
/// This is a Flutter Dart package project. It doesn't have any native
/// components, only Dart.
package
,
/// This is a native plugin project.
plugin
,
}
extension
FlutterProjectTypeExtension
on
FlutterProjectType
{
String
get
name
=>
getEnumName
(
this
);
}
FlutterProjectType
stringToProjectType
(
String
value
)
{
FlutterProjectType
result
;
for
(
final
FlutterProjectType
type
in
FlutterProjectType
.
values
)
{
if
(
value
==
type
.
name
)
{
result
=
type
;
break
;
}
}
return
result
;
}
/// A wrapper around the `.metadata` file.
class
FlutterProjectMetadata
{
FlutterProjectMetadata
(
File
metadataFile
,
Logger
logger
,
)
:
_metadataFile
=
metadataFile
,
_logger
=
logger
;
final
File
_metadataFile
;
final
Logger
_logger
;
String
get
versionChannel
=>
_versionValue
(
'channel'
);
String
get
versionRevision
=>
_versionValue
(
'revision'
);
FlutterProjectType
get
projectType
{
final
dynamic
projectTypeYaml
=
_metadataValue
(
'project_type'
);
if
(
projectTypeYaml
is
String
)
{
return
stringToProjectType
(
projectTypeYaml
);
}
else
{
_logger
.
printTrace
(
'.metadata project_type version is malformed.'
);
return
null
;
}
}
YamlMap
_versionYaml
;
String
_versionValue
(
String
key
)
{
if
(
_versionYaml
==
null
)
{
final
dynamic
versionYaml
=
_metadataValue
(
'version'
);
if
(
versionYaml
is
YamlMap
)
{
_versionYaml
=
versionYaml
;
}
else
{
_logger
.
printTrace
(
'.metadata version is malformed.'
);
return
null
;
}
}
if
(
_versionYaml
!=
null
&&
_versionYaml
.
containsKey
(
key
)
&&
_versionYaml
[
key
]
is
String
)
{
return
_versionYaml
[
key
]
as
String
;
}
return
null
;
}
YamlMap
_metadataYaml
;
dynamic
_metadataValue
(
String
key
)
{
if
(
_metadataYaml
==
null
)
{
if
(!
_metadataFile
.
existsSync
())
{
return
null
;
}
final
dynamic
metadataYaml
=
loadYaml
(
_metadataFile
.
readAsStringSync
());
if
(
metadataYaml
is
YamlMap
)
{
_metadataYaml
=
metadataYaml
;
}
else
{
_logger
.
printTrace
(
'.metadata is malformed.'
);
return
null
;
}
}
return
_metadataYaml
[
key
];
}
}
packages/flutter_tools/lib/src/globals.dart
View file @
ce40fbaf
...
...
@@ -30,6 +30,7 @@ import 'ios/xcodeproj.dart';
import
'macos/cocoapods.dart'
;
import
'macos/xcode.dart'
;
import
'persistent_tool_state.dart'
;
import
'project.dart'
;
import
'reporting/reporting.dart'
;
import
'version.dart'
;
import
'web/chrome.dart'
;
...
...
@@ -42,6 +43,7 @@ Logger get logger => context.get<Logger>();
OperatingSystemUtils
get
os
=>
context
.
get
<
OperatingSystemUtils
>();
PersistentToolState
get
persistentToolState
=>
PersistentToolState
.
instance
;
Usage
get
flutterUsage
=>
context
.
get
<
Usage
>();
FlutterProjectFactory
get
projectFactory
=>
context
.
get
<
FlutterProjectFactory
>()
??
FlutterProjectFactory
();
const
FileSystem
_kLocalFs
=
LocalFileSystem
();
...
...
packages/flutter_tools/lib/src/project.dart
View file @
ce40fbaf
...
...
@@ -11,7 +11,6 @@ import 'package:yaml/yaml.dart';
import
'android/gradle_utils.dart'
as
gradle
;
import
'artifacts.dart'
;
import
'base/common.dart'
;
import
'base/context.dart'
;
import
'base/file_system.dart'
;
import
'build_info.dart'
;
import
'bundle.dart'
as
bundle
;
...
...
@@ -24,8 +23,6 @@ import 'platform_plugins.dart';
import
'plugins.dart'
;
import
'template.dart'
;
FlutterProjectFactory
get
projectFactory
=>
context
.
get
<
FlutterProjectFactory
>()
??
FlutterProjectFactory
();
class
FlutterProjectFactory
{
FlutterProjectFactory
();
...
...
@@ -69,7 +66,7 @@ class FlutterProject {
/// Returns a [FlutterProject] view of the given directory or a ToolExit error,
/// if `pubspec.yaml` or `example/pubspec.yaml` is invalid.
static
FlutterProject
fromDirectory
(
Directory
directory
)
=>
projectFactory
.
fromDirectory
(
directory
);
static
FlutterProject
fromDirectory
(
Directory
directory
)
=>
globals
.
projectFactory
.
fromDirectory
(
directory
);
/// Returns a [FlutterProject] view of the current directory or a ToolExit error,
/// if `pubspec.yaml` or `example/pubspec.yaml` is invalid.
...
...
@@ -145,6 +142,9 @@ class FlutterProject {
/// The `.packages` file of this project.
File
get
packagesFile
=>
directory
.
childFile
(
'.packages'
);
/// The `.metadata` file of this project.
File
get
metadataFile
=>
directory
.
childFile
(
'.metadata'
);
/// The `.flutter-plugins` file of this project.
File
get
flutterPluginsFile
=>
directory
.
childFile
(
'.flutter-plugins'
);
...
...
packages/flutter_tools/lib/src/reporting/github_template.dart
View file @
ce40fbaf
...
...
@@ -5,23 +5,31 @@
import
'dart:async'
;
import
'package:file/file.dart'
;
import
'package:meta/meta.dart'
;
import
'../base/context.dart'
;
import
'../base/file_system.dart'
;
import
'../base/io.dart'
;
import
'../base/
net
.dart'
;
import
'../base/
logger
.dart'
;
import
'../convert.dart'
;
import
'../flutter_manifest.dart'
;
import
'../
globals.dart'
as
globals
;
import
'../
flutter_project_metadata.dart'
;
import
'../project.dart'
;
/// Provide suggested GitHub issue templates to user when Flutter encounters an error.
class
GitHubTemplateCreator
{
GitHubTemplateCreator
()
:
_client
=
(
context
.
get
<
HttpClientFactory
>()
==
null
)
?
HttpClient
()
:
context
.
get
<
HttpClientFactory
>()();
GitHubTemplateCreator
({
@required
FileSystem
fileSystem
,
@required
Logger
logger
,
@required
FlutterProjectFactory
flutterProjectFactory
,
@required
HttpClient
client
,
})
:
_fileSystem
=
fileSystem
,
_logger
=
logger
,
_flutterProjectFactory
=
flutterProjectFactory
,
_client
=
client
;
final
FileSystem
_fileSystem
;
final
Logger
_logger
;
final
FlutterProjectFactory
_flutterProjectFactory
;
final
HttpClient
_client
;
Future
<
String
>
toolCrashSimilarIssuesGitHubURL
(
String
errorString
)
async
{
...
...
@@ -76,7 +84,7 @@ ${_projectMetadataInformation()}
String
_projectMetadataInformation
()
{
FlutterProject
project
;
try
{
project
=
FlutterProject
.
current
(
);
project
=
_flutterProjectFactory
.
fromDirectory
(
_fileSystem
.
currentDirectory
);
}
on
Exception
catch
(
exception
)
{
// pubspec may be malformed.
return
exception
.
toString
();
...
...
@@ -86,14 +94,18 @@ ${_projectMetadataInformation()}
if
(
project
==
null
||
manifest
==
null
||
manifest
.
isEmpty
)
{
return
'No pubspec in working directory.'
;
}
final
FlutterProjectMetadata
metadata
=
FlutterProjectMetadata
(
project
.
metadataFile
,
_logger
);
final
StringBuffer
description
=
StringBuffer
()
..
writeln
(
'**Type**:
${metadata.projectType?.name}
'
)
..
writeln
(
'**Version**:
${manifest.appVersion}
'
)
..
writeln
(
'**Material**:
${manifest.usesMaterialDesign}
'
)
..
writeln
(
'**Android X**:
${manifest.usesAndroidX}
'
)
..
writeln
(
'**Module**:
${manifest.isModule}
'
)
..
writeln
(
'**Plugin**:
${manifest.isPlugin}
'
)
..
writeln
(
'**Android package**:
${manifest.androidPackage}
'
)
..
writeln
(
'**iOS bundle identifier**:
${manifest.iosBundleIdentifier}
'
);
..
writeln
(
'**iOS bundle identifier**:
${manifest.iosBundleIdentifier}
'
)
..
writeln
(
'**Creation channel**:
${metadata.versionChannel}
'
)
..
writeln
(
'**Creation framework version**:
${metadata.versionRevision}
'
);
final
File
file
=
project
.
flutterPluginsFile
;
if
(
file
.
existsSync
())
{
...
...
@@ -107,7 +119,7 @@ ${_projectMetadataInformation()}
}
// Write the last part of the path, which includes the plugin name and version.
// Example: camera-0.5.7+2
final
List
<
String
>
pathParts
=
globals
.
fs
.
path
.
split
(
pluginParts
[
1
]);
final
List
<
String
>
pathParts
=
_fileSystem
.
path
.
split
(
pluginParts
[
1
]);
description
.
writeln
(
pathParts
.
isEmpty
?
pluginParts
.
first
:
pathParts
.
last
);
}
}
...
...
@@ -124,7 +136,7 @@ ${_projectMetadataInformation()}
Future
<
String
>
_shortURL
(
String
fullURL
)
async
{
String
url
;
try
{
globals
.
printTrace
(
'Attempting git.io shortener:
$fullURL
'
);
_logger
.
printTrace
(
'Attempting git.io shortener:
$fullURL
'
);
final
List
<
int
>
bodyBytes
=
utf8
.
encode
(
'url=
${Uri.encodeQueryComponent(fullURL)}
'
);
final
HttpClientRequest
request
=
await
_client
.
postUrl
(
Uri
.
parse
(
'https://git.io'
));
request
.
headers
.
set
(
HttpHeaders
.
contentLengthHeader
,
bodyBytes
.
length
.
toString
());
...
...
@@ -134,10 +146,10 @@ ${_projectMetadataInformation()}
if
(
response
.
statusCode
==
201
)
{
url
=
response
.
headers
[
HttpHeaders
.
locationHeader
]?.
first
;
}
else
{
globals
.
printTrace
(
'Failed to shorten GitHub template URL. Server responded with HTTP status code
${response.statusCode}
'
);
_logger
.
printTrace
(
'Failed to shorten GitHub template URL. Server responded with HTTP status code
${response.statusCode}
'
);
}
}
on
Exception
catch
(
sendError
)
{
globals
.
printTrace
(
'Failed to shorten GitHub template URL:
$sendError
'
);
_logger
.
printTrace
(
'Failed to shorten GitHub template URL:
$sendError
'
);
}
return
url
??
fullURL
;
...
...
packages/flutter_tools/test/general.shard/flutter_project_metadata_test.dart
0 → 100644
View file @
ce40fbaf
// 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
'package:flutter_tools/src/flutter_project_metadata.dart'
;
import
'package:flutter_tools/src/base/file_system.dart'
;
import
'package:flutter_tools/src/base/logger.dart'
;
import
'package:file/memory.dart'
;
import
'../src/common.dart'
;
void
main
(
)
{
FileSystem
fileSystem
;
BufferLogger
logger
;
File
metadataFile
;
setUp
(()
{
fileSystem
=
MemoryFileSystem
.
test
();
logger
=
BufferLogger
.
test
();
metadataFile
=
fileSystem
.
file
(
'.metadata'
);
});
testWithoutContext
(
'project metadata fields are empty when file does not exist'
,
()
{
final
FlutterProjectMetadata
projectMetadata
=
FlutterProjectMetadata
(
metadataFile
,
logger
);
expect
(
projectMetadata
.
projectType
,
isNull
);
expect
(
projectMetadata
.
versionChannel
,
isNull
);
expect
(
projectMetadata
.
versionRevision
,
isNull
);
expect
(
logger
.
traceText
,
contains
(
'.metadata project_type version is malformed.'
));
expect
(
logger
.
traceText
,
contains
(
'.metadata version is malformed.'
));
});
testWithoutContext
(
'project metadata fields are empty when file is empty'
,
()
{
metadataFile
.
createSync
();
final
FlutterProjectMetadata
projectMetadata
=
FlutterProjectMetadata
(
metadataFile
,
logger
);
expect
(
projectMetadata
.
projectType
,
isNull
);
expect
(
projectMetadata
.
versionChannel
,
isNull
);
expect
(
projectMetadata
.
versionRevision
,
isNull
);
expect
(
logger
.
traceText
,
contains
(
'.metadata project_type version is malformed.'
));
expect
(
logger
.
traceText
,
contains
(
'.metadata version is malformed.'
));
});
testWithoutContext
(
'projectType is populated when version is malformed'
,
()
{
metadataFile
..
createSync
()
..
writeAsStringSync
(
'''
version: STRING INSTEAD OF MAP
project_type: plugin
'''
);
final
FlutterProjectMetadata
projectMetadata
=
FlutterProjectMetadata
(
metadataFile
,
logger
);
expect
(
projectMetadata
.
projectType
,
FlutterProjectType
.
plugin
);
expect
(
projectMetadata
.
versionChannel
,
isNull
);
expect
(
projectMetadata
.
versionRevision
,
isNull
);
expect
(
logger
.
traceText
,
contains
(
'.metadata version is malformed.'
));
});
testWithoutContext
(
'version is populated when projectType is malformed'
,
()
{
metadataFile
..
createSync
()
..
writeAsStringSync
(
'''
version:
revision: b59b226a49391949247e3d6122e34bb001049ae4
channel: stable
project_type: {}
'''
);
final
FlutterProjectMetadata
projectMetadata
=
FlutterProjectMetadata
(
metadataFile
,
logger
);
expect
(
projectMetadata
.
projectType
,
isNull
);
expect
(
projectMetadata
.
versionChannel
,
'stable'
);
expect
(
projectMetadata
.
versionRevision
,
'b59b226a49391949247e3d6122e34bb001049ae4'
);
expect
(
logger
.
traceText
,
contains
(
'.metadata project_type version is malformed.'
));
});
}
\ No newline at end of file
packages/flutter_tools/test/general.shard/github_template_test.dart
View file @
ce40fbaf
...
...
@@ -5,7 +5,8 @@
import
'package:file/file.dart'
;
import
'package:file/memory.dart'
;
import
'package:flutter_tools/src/base/io.dart'
;
import
'package:flutter_tools/src/base/net.dart'
;
import
'package:flutter_tools/src/base/logger.dart'
;
import
'package:flutter_tools/src/project.dart'
;
import
'package:flutter_tools/src/reporting/github_template.dart'
;
import
'../src/common.dart'
;
...
...
@@ -15,29 +16,39 @@ import '../src/testbed.dart';
const
String
_kShortURL
=
'https://www.example.com/short'
;
void
main
(
)
{
BufferLogger
logger
;
FileSystem
fs
;
setUp
(()
{
logger
=
BufferLogger
.
test
();
fs
=
MemoryFileSystem
();
});
group
(
'GitHub template creator'
,
()
{
testUsingContext
(
'similar issues URL'
,
()
async
{
final
GitHubTemplateCreator
creator
=
GitHubTemplateCreator
();
testWithoutContext
(
'similar issues URL'
,
()
async
{
final
GitHubTemplateCreator
creator
=
GitHubTemplateCreator
(
fileSystem:
fs
,
logger:
logger
,
client:
SuccessShortenURLFakeHttpClient
(),
flutterProjectFactory:
FlutterProjectFactory
(),
);
expect
(
await
creator
.
toolCrashSimilarIssuesGitHubURL
(
'this is a 100% error'
),
_kShortURL
);
},
overrides:
<
Type
,
Generator
>{
HttpClientFactory:
()
=>
()
=>
SuccessShortenURLFakeHttpClient
(),
FileSystem:
()
=>
MemoryFileSystem
(),
ProcessManager:
()
=>
FakeProcessManager
.
any
(),
});
testUsingContext
(
'similar issues URL with network failure'
,
()
async
{
final
GitHubTemplateCreator
creator
=
GitHubTemplateCreator
();
testWithoutContext
(
'similar issues URL with network failure'
,
()
async
{
final
GitHubTemplateCreator
creator
=
GitHubTemplateCreator
(
fileSystem:
fs
,
logger:
logger
,
client:
FakeHttpClient
(),
flutterProjectFactory:
FlutterProjectFactory
(),
);
expect
(
await
creator
.
toolCrashSimilarIssuesGitHubURL
(
'this is a 100% error'
),
'https://github.com/flutter/flutter/issues?q=is%3Aissue+this+is+a+100%25+error'
);
},
overrides:
<
Type
,
Generator
>{
HttpClientFactory:
()
=>
()
=>
FakeHttpClient
(),
FileSystem:
()
=>
MemoryFileSystem
(),
ProcessManager:
()
=>
FakeProcessManager
.
any
(),
expect
(
logger
.
traceText
,
contains
(
'Failed to shorten GitHub template URL'
));
});
group
(
'new issue template URL'
,
()
{
...
...
@@ -46,27 +57,34 @@ void main() {
const
String
errorString
=
'this is a 100% error'
;
const
String
exception
=
'failing to succeed!!!'
;
const
String
doctorText
=
' [✓] Flutter (Channel report'
;
FileSystem
fs
;
setUp
(()
async
{
stackTrace
=
StackTrace
.
fromString
(
'trace'
);
fs
=
MemoryFileSystem
();
});
testUsingContext
(
'shortened'
,
()
async
{
final
GitHubTemplateCreator
creator
=
GitHubTemplateCreator
();
final
GitHubTemplateCreator
creator
=
GitHubTemplateCreator
(
fileSystem:
fs
,
logger:
logger
,
client:
SuccessShortenURLFakeHttpClient
(),
flutterProjectFactory:
FlutterProjectFactory
(),
);
expect
(
await
creator
.
toolCrashIssueTemplateGitHubURL
(
command
,
errorString
,
exception
,
stackTrace
,
doctorText
),
_kShortURL
);
},
overrides:
<
Type
,
Generator
>{
HttpClientFactory:
()
=>
()
=>
SuccessShortenURLFakeHttpClient
(),
FileSystem:
()
=>
MemoryFileSystem
(),
ProcessManager:
()
=>
FakeProcessManager
.
any
(),
});
testUsingContext
(
'with network failure'
,
()
async
{
final
GitHubTemplateCreator
creator
=
GitHubTemplateCreator
();
final
GitHubTemplateCreator
creator
=
GitHubTemplateCreator
(
fileSystem:
fs
,
logger:
logger
,
client:
FakeHttpClient
(),
flutterProjectFactory:
FlutterProjectFactory
(),
);
expect
(
await
creator
.
toolCrashIssueTemplateGitHubURL
(
command
,
errorString
,
exception
,
stackTrace
,
doctorText
),
'https://github.com/flutter/flutter/issues/new?title=%5Btool_crash%5D+this+is+a+100%25+error&body=%23%'
...
...
@@ -75,16 +93,20 @@ void main() {
'%60%60%60%0A%60%60%60%0A+%5B%E2%9C%93%5D+Flutter+%28Channel+report%0A%60%60%60%0A%0A%23%23'
'+Flutter+Application+Metadata%0ANo+pubspec+in+working+directory.%0A&labels=tool%2Csevere%3A+crash'
);
expect
(
logger
.
traceText
,
contains
(
'Failed to shorten GitHub template URL'
));
},
overrides:
<
Type
,
Generator
>{
HttpClientFactory:
()
=>
()
=>
FakeHttpClient
(),
FileSystem:
()
=>
MemoryFileSystem
(),
ProcessManager:
()
=>
FakeProcessManager
.
any
(),
});
testUsingContext
(
'app metadata'
,
()
async
{
final
GitHubTemplateCreator
creator
=
GitHubTemplateCreator
();
final
GitHubTemplateCreator
creator
=
GitHubTemplateCreator
(
fileSystem:
fs
,
logger:
logger
,
client:
FakeHttpClient
(),
flutterProjectFactory:
FlutterProjectFactory
(),
);
final
Directory
projectDirectory
=
fs
.
currentDirectory
;
final
File
pluginsFile
=
projectDirectory
.
childFile
(
'.flutter-plugins'
);
projectDirectory
.
childFile
(
'pubspec.yaml'
)
...
...
@@ -99,12 +121,23 @@ flutter:
iosBundleIdentifier: com.example.failing.ios
'''
);
final
File
pluginsFile
=
projectDirectory
.
childFile
(
'.flutter-plugins'
);
pluginsFile
.
writeAsStringSync
(
'''
camera=/fake/pub.dartlang.org/camera-0.5.7+2/
device_info=/fake/pub.dartlang.org/pub.dartlang.org/device_info-0.4.1+4/
'''
);
final
File
metadataFile
=
projectDirectory
.
childFile
(
'.metadata'
);
metadataFile
.
writeAsStringSync
(
'''
version:
revision: 0b8abb4724aa590dd0f429683339b1e045a1594d
channel: stable
project_type: app
'''
);
final
String
actualURL
=
await
creator
.
toolCrashIssueTemplateGitHubURL
(
command
,
errorString
,
exception
,
stackTrace
,
doctorText
);
final
String
actualBody
=
Uri
.
parse
(
actualURL
).
queryParameters
[
'body'
];
const
String
expectedBody
=
'''
...
...
@@ -128,6 +161,7 @@ trace
```
## Flutter Application Metadata
**Type**: app
**Version**: 2.0.1+100
**Material**: true
**Android X**: true
...
...
@@ -135,6 +169,8 @@ trace
**Plugin**: false
**Android package**: com.example.failing.android
**iOS bundle identifier**: com.example.failing.ios
**Creation channel**: stable
**Creation framework version**: 0b8abb4724aa590dd0f429683339b1e045a1594d
### Plugins
camera-0.5.7+2
device_info-0.4.1+4
...
...
@@ -143,7 +179,6 @@ device_info-0.4.1+4
expect
(
actualBody
,
expectedBody
);
},
overrides:
<
Type
,
Generator
>{
HttpClientFactory:
()
=>
()
=>
FakeHttpClient
(),
FileSystem:
()
=>
fs
,
ProcessManager:
()
=>
FakeProcessManager
.
any
(),
});
...
...
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