1
00:00:05,222 --> 00:00:06,560
At the end of the previous video,

2
00:00:06,560 --> 00:00:09,380
we ran the app and we got a security exception

3
00:00:09,380 --> 00:00:11,080
because the app didn't have permissions

4
00:00:11,080 --> 00:00:12,820
to access the Internet.

5
00:00:12,820 --> 00:00:14,290
Now, we had a look at the stack trace

6
00:00:14,290 --> 00:00:16,000
and how it's a useful way to work out

7
00:00:16,000 --> 00:00:18,220
what went wrong, and we're just gonna

8
00:00:18,220 --> 00:00:21,030
run the app again, just to get the same error

9
00:00:21,030 --> 00:00:22,930
and we can see the links in our own code

10
00:00:22,930 --> 00:00:24,190
appear in blue when I do that,

11
00:00:24,190 --> 00:00:25,590
so let's just start that up.

12
00:00:29,990 --> 00:00:32,009
Okay, so you see we've got a crash there

13
00:00:32,009 --> 00:00:34,340
and if we have a look at Logcat,

14
00:00:34,340 --> 00:00:35,760
we can come over here and scroll over

15
00:00:35,760 --> 00:00:37,453
and we can see our links in blue.

16
00:00:38,390 --> 00:00:39,540
I can click on that first link

17
00:00:39,540 --> 00:00:40,990
and that takes us to line 51.

18
00:00:41,941 --> 00:00:44,080
You can see that the error happened

19
00:00:44,080 --> 00:00:46,510
when we tried to do anything with the connection,

20
00:00:46,510 --> 00:00:49,740
in this case, even just reading the response code.

21
00:00:49,740 --> 00:00:51,500
The problem was with the Internet connection

22
00:00:51,500 --> 00:00:54,150
and the fact that it's a security exception

23
00:00:54,150 --> 00:00:57,630
really provides all the remaining information we need.

24
00:00:57,630 --> 00:01:00,200
Just to confirm that it is a security exception again,

25
00:01:00,200 --> 00:01:02,200
let's scroll up and have a look.

26
00:01:02,200 --> 00:01:05,740
Java.lang.SecurityException permission denied

27
00:01:05,740 --> 00:01:06,970
and I got a suggestion there for

28
00:01:06,970 --> 00:01:08,870
missing Internet permissions, perhaps.

29
00:01:09,780 --> 00:01:11,200
Before we look at fixing the problem

30
00:01:11,200 --> 00:01:13,300
which is obviously something we need to do,

31
00:01:13,300 --> 00:01:15,040
let's catch that exception and make

32
00:01:15,040 --> 00:01:17,370
all those error messages a bit tidier

33
00:01:17,370 --> 00:01:19,640
instead of showing the full stack trace.

34
00:01:19,640 --> 00:01:23,054
I'm going to close down the Logcat for now.

35
00:01:23,054 --> 00:01:25,745
We're going to add another catch here

36
00:01:25,745 --> 00:01:28,760
and we're going to put the original exception

37
00:01:28,760 --> 00:01:31,470
back again now, but above that,

38
00:01:31,470 --> 00:01:34,250
what I'm going to do is add another catch

39
00:01:36,020 --> 00:01:38,000
for our security exception.

40
00:01:38,000 --> 00:01:41,473
The catch, e: SecurityException.

41
00:01:45,410 --> 00:01:46,470
Then a code block, and we're gonna do

42
00:01:46,470 --> 00:01:50,770
a Log.e, parentheses tag, comma.

43
00:01:50,770 --> 00:01:54,530
That's gonna be downloadXML: security exception,

44
00:02:01,540 --> 00:02:04,630
needs permission, then we'll put

45
00:02:04,630 --> 00:02:08,002
a dollar sign, left and right curly braces, e.message.

46
00:02:09,250 --> 00:02:11,530
Let's try running that again now.

47
00:02:11,530 --> 00:02:13,330
It should prevent us from getting that

48
00:02:13,330 --> 00:02:15,970
big exception, big stack trace, rather

49
00:02:17,830 --> 00:02:20,513
but we should still see our error logged.

50
00:02:20,513 --> 00:02:22,020
Now it's no longer crashing, but if

51
00:02:22,020 --> 00:02:23,790
we have a look at our Logcat,

52
00:02:23,790 --> 00:02:25,220
you can see I've got a security exception,

53
00:02:25,220 --> 00:02:26,900
needs permission, and then we've got

54
00:02:26,900 --> 00:02:28,410
the message that's coming back from

55
00:02:28,410 --> 00:02:30,550
the actual exception itself,

56
00:02:30,550 --> 00:02:33,030
permission denied, missing Internet permission.

57
00:02:33,030 --> 00:02:36,290
Then of course we've got error downloading as a result.

58
00:02:36,290 --> 00:02:38,370
While we've got some good errors in the Logcat,

59
00:02:38,370 --> 00:02:40,190
I'm gonna digress briefly and show you

60
00:02:40,190 --> 00:02:42,700
a bit more about the Logcat and how you can

61
00:02:42,700 --> 00:02:45,360
make it easier to find information in it.

62
00:02:45,360 --> 00:02:47,690
I'm gonna start by clearing the filter

63
00:02:47,690 --> 00:02:49,093
by clicking on X over here,

64
00:02:50,450 --> 00:02:52,370
and now you can just see how busy the Logcat gets.

65
00:02:52,370 --> 00:02:53,610
There's lots of other information

66
00:02:53,610 --> 00:02:55,620
that we've been filtering out

67
00:02:55,620 --> 00:02:57,390
but we can filter that using the box

68
00:02:57,390 --> 00:03:00,550
near the top right of the AndroidMonitor pane.

69
00:03:00,550 --> 00:03:01,850
Again, you've seen this before,

70
00:03:01,850 --> 00:03:03,350
but if I type in downloaddata,

71
00:03:06,860 --> 00:03:08,260
then we'll only see messages logged

72
00:03:08,260 --> 00:03:11,100
by our downloaddata class, but curiously,

73
00:03:11,100 --> 00:03:13,150
this is sort of case sensitive.

74
00:03:13,150 --> 00:03:16,730
If I delete this and I start the word download

75
00:03:16,730 --> 00:03:18,503
with a capital D, download,

76
00:03:20,960 --> 00:03:22,910
to match the tag that appears in the log,

77
00:03:22,910 --> 00:03:24,270
and you have to continue matching

78
00:03:24,270 --> 00:03:26,710
the case exactly, so downloaddata

79
00:03:26,710 --> 00:03:29,250
will display the entries logged by the class,

80
00:03:29,250 --> 00:03:32,750
but Downloadd, so you can see here.

81
00:03:32,750 --> 00:03:34,050
I don't need to type anymore because

82
00:03:34,050 --> 00:03:37,000
you can see straight away it's not matching anything.

83
00:03:37,000 --> 00:03:38,130
The best thing to do here is to

84
00:03:38,130 --> 00:03:40,370
type all your filters in lowercase,

85
00:03:40,370 --> 00:03:44,423
so downloaddata, which then works again.

86
00:03:45,745 --> 00:03:46,850
Now that I've done that and typed in

87
00:03:46,850 --> 00:03:48,740
downloaddata into the filter box,

88
00:03:48,740 --> 00:03:51,003
we can see the doInBackground starting.

89
00:03:51,940 --> 00:03:54,080
Starts with, and then the link

90
00:03:54,080 --> 00:03:55,630
and the URL that received, obviously,

91
00:03:55,630 --> 00:03:58,300
and it also logs an error after the error

92
00:03:58,300 --> 00:04:02,210
from downloadXML catching the security exception.

93
00:04:02,210 --> 00:04:05,040
Finally, onPostExecute is logging

94
00:04:05,040 --> 00:04:06,430
its parameter as an empty string

95
00:04:06,430 --> 00:04:11,430
which is what we'd expect if doInBackground gave an error.

96
00:04:11,430 --> 00:04:14,120
Again, when I delete the contents or clear it

97
00:04:14,120 --> 00:04:17,567
by clicking on the X, we get heaps of messages again.

98
00:04:17,567 --> 00:04:19,630
Now, this would contain far more

99
00:04:19,630 --> 00:04:22,650
on a physical device, but even an emulator

100
00:04:22,650 --> 00:04:25,490
is continuously logging all sorts of stuff.

101
00:04:25,490 --> 00:04:27,220
In fact, if I change this dropdown here

102
00:04:27,220 --> 00:04:31,130
to the right to no filters and scroll up,

103
00:04:32,850 --> 00:04:35,040
you can see now that there's an absolute load

104
00:04:35,040 --> 00:04:36,380
of things that have been logged here.

105
00:04:36,380 --> 00:04:38,270
Heaps of things, and you can see

106
00:04:38,270 --> 00:04:42,110
there's just pages and pages and pages of stuff there.

107
00:04:42,110 --> 00:04:43,550
I'm gonna change that back to show only

108
00:04:43,550 --> 00:04:47,472
selected applications again, application I should say.

109
00:04:47,472 --> 00:04:50,660
We're just getting stuff that's relevant for us.

110
00:04:50,660 --> 00:04:52,560
The selected application it's referring to

111
00:04:52,560 --> 00:04:54,980
by the way is the one in the second dropdown

112
00:04:54,980 --> 00:04:56,350
from the left, this one here,

113
00:04:56,350 --> 00:04:57,370
which is obviously our app,

114
00:04:57,370 --> 00:05:00,563
our academy.learnprogramming.top10downloader.

115
00:05:01,490 --> 00:05:03,560
Now Android devices have quite a few things

116
00:05:03,560 --> 00:05:05,330
going on at once, so you can actually

117
00:05:05,330 --> 00:05:08,070
look at logs for other applications if you want

118
00:05:08,070 --> 00:05:09,100
but unless you're getting involved

119
00:05:09,100 --> 00:05:10,820
in Android system programming,

120
00:05:10,820 --> 00:05:12,910
you generally just want to leave it to display

121
00:05:12,910 --> 00:05:14,710
just the entries for your app.

122
00:05:14,710 --> 00:05:16,960
If you do want a full stack trace to be printed

123
00:05:16,960 --> 00:05:19,450
when you've caught an exception, you can do that.

124
00:05:19,450 --> 00:05:22,120
I'll just go back here, back to our code,

125
00:05:22,120 --> 00:05:23,220
close down the Logcat.

126
00:05:24,546 --> 00:05:26,090
You can do that by calling

127
00:05:26,090 --> 00:05:28,690
the printStackTrace method of the exception,

128
00:05:28,690 --> 00:05:30,310
so I'm gonna add that to the catch block

129
00:05:30,310 --> 00:05:32,640
for the security exception just to show you.

130
00:05:32,640 --> 00:05:35,450
I'm gonna actually do that before the log.

131
00:05:35,450 --> 00:05:36,708
It doesn't really matter where we do it

132
00:05:36,708 --> 00:05:37,570
but we'll do it before.

133
00:05:37,570 --> 00:05:40,613
We'll do it e.printStackTrace.

134
00:05:41,892 --> 00:05:43,140
Let's go back to the Logcat and make sure that

135
00:05:43,140 --> 00:05:45,770
I have cleared the filter so it doesn't

136
00:05:45,770 --> 00:05:47,540
filter out most of the stack trace.

137
00:05:47,540 --> 00:05:50,080
Basically, I'm gonna get more data by doing that.

138
00:05:50,080 --> 00:05:51,130
Now that I've made that change

139
00:05:51,130 --> 00:05:53,260
let's try running it again.

140
00:05:53,260 --> 00:05:54,190
What I'll do first is I'll actually

141
00:05:54,190 --> 00:05:57,520
clear the filter as well there, clear the Logcat.

142
00:05:57,520 --> 00:05:58,570
We'll run that again.

143
00:06:04,470 --> 00:06:06,453
You can see now that we've done that,

144
00:06:08,290 --> 00:06:11,110
we've printed out quite a bit of stuff there.

145
00:06:11,110 --> 00:06:12,370
Basically, that's the stack trace

146
00:06:12,370 --> 00:06:14,470
that we had before I caught the exception.

147
00:06:15,330 --> 00:06:18,380
You can see scrolling up that it's actually done that.

148
00:06:18,380 --> 00:06:20,870
Android Studio doesn't colour the messages red

149
00:06:20,870 --> 00:06:22,200
and that's because they're created

150
00:06:22,200 --> 00:06:24,830
deliberately by our app now rather than

151
00:06:24,830 --> 00:06:26,960
by the Java Runtime, but the links

152
00:06:26,960 --> 00:06:29,240
in the the code, if we scroll down

153
00:06:29,240 --> 00:06:31,190
and have a look over here to the right,

154
00:06:32,830 --> 00:06:34,420
they're still a different colour.

155
00:06:34,420 --> 00:06:36,820
We can still click on mainactivity.kt

156
00:06:36,820 --> 00:06:40,500
and get to line 51 and see where the error actually is.

157
00:06:40,500 --> 00:06:41,550
Basically, it's the same line of code

158
00:06:41,550 --> 00:06:45,820
that our response equals, connection.responseCode.

159
00:06:45,820 --> 00:06:48,020
Something else we can do, as I mentioned earlier,

160
00:06:48,020 --> 00:06:50,060
is filter out more than one term

161
00:06:50,060 --> 00:06:51,480
and it'd be useful to get some idea

162
00:06:51,480 --> 00:06:53,220
of what's happening through MainActivity

163
00:06:53,220 --> 00:06:54,460
and we can do that by filtering

164
00:06:54,460 --> 00:06:56,620
from MainActivity or downloaddata.

165
00:06:56,620 --> 00:06:57,630
We have seen this before,

166
00:06:57,630 --> 00:07:00,160
but we'll just briefly show that again.

167
00:07:00,160 --> 00:07:01,310
So that's mainactivity.

168
00:07:04,630 --> 00:07:06,110
You've seen the use of this pipe

169
00:07:06,110 --> 00:07:08,217
or bar character before, vertical bar,

170
00:07:08,217 --> 00:07:10,320
which actually means or.

171
00:07:10,320 --> 00:07:11,777
You can type downloaddata,

172
00:07:12,817 --> 00:07:14,850
and now we're getting information

173
00:07:14,850 --> 00:07:17,146
about MainActivity or downloaddata,

174
00:07:17,146 --> 00:07:19,620
so the vertical bar means or, basically.

175
00:07:19,620 --> 00:07:20,840
Alright, so that cleans everything up

176
00:07:20,840 --> 00:07:22,490
and we can see onCreate being started

177
00:07:22,490 --> 00:07:25,437
in MainActivity over here, as well as

178
00:07:25,437 --> 00:07:28,340
the log entries from the DownloadData class.

179
00:07:28,340 --> 00:07:30,812
Okay, so I'm gonna close Logcat for now.

180
00:07:30,812 --> 00:07:33,730
Let's talk about permissions.

181
00:07:33,730 --> 00:07:37,210
By default, an app has no permissions to anything at all.

182
00:07:37,210 --> 00:07:39,010
An app has to get permission from the user

183
00:07:39,010 --> 00:07:41,600
to access resources it needs and this was

184
00:07:41,600 --> 00:07:43,500
usually done when the app's installed.

185
00:07:45,370 --> 00:07:46,872
Now I say was, as you can see on the screen there,

186
00:07:46,872 --> 00:07:50,400
because with Android 6.0, Marshmallow,

187
00:07:50,400 --> 00:07:52,140
Google changed the way that an app

188
00:07:52,140 --> 00:07:55,980
obtained permissions for the resources it needs.

189
00:07:55,980 --> 00:07:58,266
Prior to Android Marshmallow, the user granted

190
00:07:58,266 --> 00:08:01,400
the requested permissions when they installed the app.

191
00:08:01,400 --> 00:08:03,490
If they didn't grant all the permissions,

192
00:08:03,490 --> 00:08:05,710
then the app couldn't be installed.

193
00:08:05,710 --> 00:08:09,270
Once granted, the app had all the requested permissions

194
00:08:09,270 --> 00:08:12,310
for its entire lifetime on the device.

195
00:08:12,310 --> 00:08:13,830
The only way to revoke any of the permissions

196
00:08:13,830 --> 00:08:15,680
was effectively to uninstall the app.

197
00:08:16,720 --> 00:08:19,890
With Marshmallow and above, an app requests

198
00:08:19,890 --> 00:08:22,227
the permissions it needs when it runs

199
00:08:22,227 --> 00:08:25,300
and it has to do so each time it is run.

200
00:08:25,300 --> 00:08:27,530
Now actually Google documentation states

201
00:08:27,530 --> 00:08:29,830
even if the app used the camera yesterday,

202
00:08:29,830 --> 00:08:33,169
it can't assume it still has that permission today.

203
00:08:33,169 --> 00:08:35,860
The documentation isn't as clear as it could be

204
00:08:35,860 --> 00:08:37,820
and if you read it in a certain way,

205
00:08:37,820 --> 00:08:39,390
it could be implying that your app

206
00:08:39,390 --> 00:08:41,600
has to request the permission from the user

207
00:08:41,600 --> 00:08:45,210
each time it runs, but that isn't the case fortunately.

208
00:08:45,210 --> 00:08:47,720
Once the user has granted a permission,

209
00:08:47,720 --> 00:08:50,220
then your app continues to have that permission

210
00:08:50,220 --> 00:08:52,910
unless the user specifically revokes it.

211
00:08:52,910 --> 00:08:54,750
The app still has to request the permission

212
00:08:54,750 --> 00:08:56,800
each time but the Android system

213
00:08:56,800 --> 00:08:59,003
doesn't ask the user every time.

214
00:09:01,270 --> 00:09:02,190
Alright, so let's have a look at

215
00:09:02,190 --> 00:09:03,740
the documentation because apart from

216
00:09:03,740 --> 00:09:06,750
that one source of confusion, it's pretty good.

217
00:09:06,750 --> 00:09:08,550
Google separates their documentation

218
00:09:08,550 --> 00:09:11,200
into reference, guides, and tutorials

219
00:09:11,200 --> 00:09:14,590
and the tutorial pages for permissions explains it all.

220
00:09:14,590 --> 00:09:16,490
I'm gonna just open that in a browser.

221
00:09:19,450 --> 00:09:21,440
Paste the link there.

222
00:09:21,440 --> 00:09:23,060
Now this first page explains that

223
00:09:23,060 --> 00:09:26,440
each app runs in its own sandbox.

224
00:09:26,440 --> 00:09:28,240
Elsewhere in the documentation explains

225
00:09:28,240 --> 00:09:30,180
how this is achieved, which is by

226
00:09:30,180 --> 00:09:32,910
creating a new Linux user ID for each app,

227
00:09:32,910 --> 00:09:34,340
but we don't need to understand that

228
00:09:34,340 --> 00:09:36,930
level of data to work with permissions.

229
00:09:36,930 --> 00:09:39,890
The getting started link down here at the bottom

230
00:09:39,890 --> 00:09:42,240
goes into a bit more detail, so click that,

231
00:09:42,240 --> 00:09:43,700
and it starts by saying the app

232
00:09:43,700 --> 00:09:45,320
has to declare the permissions

233
00:09:45,320 --> 00:09:47,520
it needs in the App Manifest.

234
00:09:47,520 --> 00:09:48,590
We're gonna be doing that for

235
00:09:48,590 --> 00:09:50,660
the Internet permission in a minute.

236
00:09:50,660 --> 00:09:53,700
In this second paragraph is a description

237
00:09:53,700 --> 00:09:57,950
of the different behaviour for Android versions up to 5.1

238
00:09:57,950 --> 00:10:00,640
and for version 6.0 and higher.

239
00:10:00,640 --> 00:10:03,770
Up to 5.1, the user grants permission

240
00:10:03,770 --> 00:10:05,230
when they instal the app.

241
00:10:05,230 --> 00:10:06,870
If they don't grant the permissions,

242
00:10:06,870 --> 00:10:08,900
then the app doesn't instal,

243
00:10:08,900 --> 00:10:11,500
but from Android 6.0 and above,

244
00:10:11,500 --> 00:10:14,320
the user grants permission when they run the app.

245
00:10:14,320 --> 00:10:16,390
It's worth going through this Google tutorial

246
00:10:16,390 --> 00:10:18,410
when you come to create your own apps,

247
00:10:18,410 --> 00:10:19,750
as there are recommendations on

248
00:10:19,750 --> 00:10:22,210
when and how you should request permissions

249
00:10:22,210 --> 00:10:23,940
when your app is running.

250
00:10:23,940 --> 00:10:26,390
Google suggests that you don't request

251
00:10:26,390 --> 00:10:28,470
all the permissions at once, but instead

252
00:10:28,470 --> 00:10:29,840
you wait until the user does something

253
00:10:29,840 --> 00:10:33,630
that needs a permission before asking them for it.

254
00:10:33,630 --> 00:10:35,060
It makes more sense to the user

255
00:10:35,060 --> 00:10:38,030
if your app asks them for permission

256
00:10:38,030 --> 00:10:40,210
to access their contacts when they've just

257
00:10:40,210 --> 00:10:41,990
tried to use your app to share a file

258
00:10:41,990 --> 00:10:43,680
with someone, for example.

259
00:10:43,680 --> 00:10:45,390
But if you request that permission

260
00:10:45,390 --> 00:10:47,550
as soon as they first run your app,

261
00:10:47,550 --> 00:10:48,810
then they may be left wondering why

262
00:10:48,810 --> 00:10:51,323
the app needs to access their contacts at all.

263
00:10:52,190 --> 00:10:53,870
There's a very useful link at the end of

264
00:10:53,870 --> 00:10:56,740
the third paragraph, down here,

265
00:10:56,740 --> 00:10:58,920
which will take you to the definition

266
00:10:58,920 --> 00:11:01,003
of normal and dangerous permissions.

267
00:11:03,030 --> 00:11:04,510
Permission to access the Internet

268
00:11:04,510 --> 00:11:07,380
counts as a normal permission and the system will

269
00:11:07,380 --> 00:11:09,470
automatically grant that permission

270
00:11:09,470 --> 00:11:12,520
as long as we declare it in the manifest.

271
00:11:12,520 --> 00:11:14,780
But scrolling down slightly,

272
00:11:14,780 --> 00:11:16,160
you can see that we've got a list here

273
00:11:16,160 --> 00:11:18,510
of dangerous permissions and permission groups

274
00:11:19,580 --> 00:11:21,450
and we can talk here about permission groups

275
00:11:21,450 --> 00:11:23,810
and I guess it goes into a bit more detail

276
00:11:23,810 --> 00:11:25,450
about the various types of permissions

277
00:11:25,450 --> 00:11:27,690
and this is dangerous permissions as well.

278
00:11:27,690 --> 00:11:29,970
A bit of an overview of what it is.

279
00:11:29,970 --> 00:11:32,350
Looking at the table, it's actually listing

280
00:11:32,350 --> 00:11:36,020
what Android or Google suggests

281
00:11:36,020 --> 00:11:38,130
are dangerous permissions.

282
00:11:38,130 --> 00:11:39,500
We're gonna be looking at how to deal with

283
00:11:39,500 --> 00:11:41,110
requesting permissions when our app is

284
00:11:41,110 --> 00:11:43,250
running later in the course, when we need

285
00:11:43,250 --> 00:11:45,890
access to the contacts and the microphone.

286
00:11:45,890 --> 00:11:48,870
I'm gonna scroll up a bit, basically up to

287
00:11:48,870 --> 00:11:50,490
the normal permissions group here,

288
00:11:50,490 --> 00:11:52,670
normal and dangerous permissions.

289
00:11:52,670 --> 00:11:54,380
There's a link there for normal permissions,

290
00:11:54,380 --> 00:11:55,730
so I'm gonna click on that.

291
00:11:57,780 --> 00:11:59,310
If we have a look you can see if we scroll down,

292
00:11:59,310 --> 00:12:03,060
Internet is defined as a normal permission

293
00:12:03,060 --> 00:12:05,020
so the good news for this app is

294
00:12:05,020 --> 00:12:06,510
we only have to declare that we need

295
00:12:06,510 --> 00:12:08,780
Internet permission in the manifest

296
00:12:08,780 --> 00:12:11,160
and the app will work on all Android versions

297
00:12:11,160 --> 00:12:12,663
that we're actually targeting.

298
00:12:13,880 --> 00:12:15,863
If we go back now to Android Studio,

299
00:12:17,450 --> 00:12:20,480
I'm going to open the Android manifest.

300
00:12:20,480 --> 00:12:22,020
If you're working in Android view,

301
00:12:22,020 --> 00:12:24,170
I suggest you really want to do that,

302
00:12:24,170 --> 00:12:27,060
you'll find the manifest in the manifests folder under app.

303
00:12:27,060 --> 00:12:29,135
If we open it up, you can see that

304
00:12:29,135 --> 00:12:31,560
I'm in Android view here, we've got manifests.

305
00:12:31,560 --> 00:12:34,960
I'm gonna click on that and there's our AndroidManifest.XML.

306
00:12:34,960 --> 00:12:36,860
I can double click on that to open it.

307
00:12:37,800 --> 00:12:39,890
Now, don't worry too much about all this stuff in here.

308
00:12:39,890 --> 00:12:41,570
We're gonna be looking at the application tag

309
00:12:41,570 --> 00:12:44,210
later on and explaining what it means.

310
00:12:44,210 --> 00:12:45,840
For now though, we need to add an entry

311
00:12:45,840 --> 00:12:49,080
to declare that the app uses the Internet.

312
00:12:49,080 --> 00:12:51,630
I'm gonna make some space at the top here,

313
00:12:51,630 --> 00:12:54,540
just after the package, before the start

314
00:12:54,540 --> 00:12:55,863
of the application tag.

315
00:12:56,790 --> 00:12:59,550
I'm gonna start typing the uses tag,

316
00:12:59,550 --> 00:13:02,183
so less than sign and then uses.

317
00:13:04,530 --> 00:13:05,710
I definitely recommend using

318
00:13:05,710 --> 00:13:07,690
the code completion feature here

319
00:13:07,690 --> 00:13:10,520
to make sure you don't make any errors when typing.

320
00:13:10,520 --> 00:13:12,200
If you get the case wrong, you won't see

321
00:13:12,200 --> 00:13:14,450
an error in here but the app won't work

322
00:13:14,450 --> 00:13:16,870
because the permission won't be granted.

323
00:13:16,870 --> 00:13:19,760
I want users-permission, I'll go to tab

324
00:13:19,760 --> 00:13:22,230
to use my arrow keys to go down to that.

325
00:13:22,230 --> 00:13:23,460
Then I'm gonna press enter or I could have

326
00:13:23,460 --> 00:13:25,320
clicked on it to select it.

327
00:13:25,320 --> 00:13:26,470
Notice that when I've done that,

328
00:13:26,470 --> 00:13:28,620
we automatically got this pop-up

329
00:13:28,620 --> 00:13:31,090
and I prefer to use the arrow keys

330
00:13:31,090 --> 00:13:33,010
to select the one I want and that's because

331
00:13:33,010 --> 00:13:34,530
I don't like switching from the keyboard or mouse

332
00:13:34,530 --> 00:13:36,854
but it's your choice as to which one you want.

333
00:13:36,854 --> 00:13:39,210
All the available permissions are shown.

334
00:13:39,210 --> 00:13:41,780
As you can see here, I can select the one I want.

335
00:13:41,780 --> 00:13:44,250
Again, these permissions are case sensitive

336
00:13:44,250 --> 00:13:46,470
so once again, I recommend that you select them

337
00:13:46,470 --> 00:13:49,610
from the list rather than typing them in.

338
00:13:49,610 --> 00:13:50,910
You can filter the list as well,

339
00:13:50,910 --> 00:13:53,221
so if I type in cam for example

340
00:13:53,221 --> 00:13:56,240
you can see that android.permission.camera

341
00:13:56,240 --> 00:13:58,120
is showing on the list, but I don't want that one

342
00:13:58,120 --> 00:14:00,850
so I'm gonna delete cam, type int instead

343
00:14:02,450 --> 00:14:03,890
and you can see we've got some of

344
00:14:03,890 --> 00:14:07,590
the other ones that have got the letters int in them.

345
00:14:07,590 --> 00:14:09,660
You can see that there's the Internet permission there,

346
00:14:09,660 --> 00:14:10,590
the second one, so I'm gonna use

347
00:14:10,590 --> 00:14:12,690
the down arrow key, I'm gonna press enter.

348
00:14:14,340 --> 00:14:15,670
You can see that's added it for us

349
00:14:15,670 --> 00:14:17,870
and I just need to close the tag

350
00:14:17,870 --> 00:14:19,260
with the forward slash, so I'm gonna

351
00:14:19,260 --> 00:14:20,810
click on the forward slash and that closes it

352
00:14:20,810 --> 00:14:22,970
and adds the last bit of the tag

353
00:14:22,970 --> 00:14:24,400
and that's the Internet permission

354
00:14:24,400 --> 00:14:27,090
declared now in the manifest.

355
00:14:27,090 --> 00:14:29,130
This time, the app should run without any errors,

356
00:14:29,130 --> 00:14:32,180
so let's run it and then have a look at the Logcat.

357
00:14:32,180 --> 00:14:33,013
Actually what we'll do is we'll open up

358
00:14:33,013 --> 00:14:36,040
the Logcat first, and we'll run it.

359
00:14:36,040 --> 00:14:37,780
Just clear the log, Logcat,

360
00:14:37,780 --> 00:14:39,130
which I've mentioned before, is a good habit

361
00:14:39,130 --> 00:14:41,100
to get into, even though Android Studio

362
00:14:41,100 --> 00:14:43,000
tends to do that for us at the moment.

363
00:14:44,450 --> 00:14:46,430
Alright, so you can see this time

364
00:14:46,430 --> 00:14:48,930
we haven't got an error anymore.

365
00:14:48,930 --> 00:14:51,080
If we scroll back up to the top,

366
00:14:51,080 --> 00:14:52,280
you can see now right at the top here

367
00:14:52,280 --> 00:14:56,540
we've got downloadXML, the response code was 200.

368
00:14:56,540 --> 00:14:58,420
That's looking good, and that means,

369
00:14:58,420 --> 00:15:02,200
the response code of 200 means OK.

370
00:15:02,200 --> 00:15:03,580
If your Internet connection goes through

371
00:15:03,580 --> 00:15:06,220
a proxy, then you might get a 203 response code

372
00:15:06,220 --> 00:15:07,723
instead but that's also fine.

373
00:15:08,760 --> 00:15:09,843
We can see the XML, you probably saw that

374
00:15:09,843 --> 00:15:12,480
just by scrolling up, and that's the XML

375
00:15:12,480 --> 00:15:14,420
printed by the onPostExecute method

376
00:15:14,420 --> 00:15:17,060
so our download's definitely working fine.

377
00:15:17,060 --> 00:15:18,690
One thing to be aware of is that

378
00:15:18,690 --> 00:15:21,400
there's a limit to how much a log entry can be,

379
00:15:21,400 --> 00:15:24,990
so you won't necessarily see all the XML in the Logcat.

380
00:15:24,990 --> 00:15:27,790
If it hadn't all downloaded there'd be an error

381
00:15:27,790 --> 00:15:30,788
so it looks like everything's fine.

382
00:15:30,788 --> 00:15:32,030
If we scroll down and have a look,

383
00:15:32,030 --> 00:15:34,210
you can see it seems to just chop it off

384
00:15:34,210 --> 00:15:37,240
but again, that's due to the limit of Logcat

385
00:15:37,240 --> 00:15:38,750
and if we saw an error, there was

386
00:15:38,750 --> 00:15:40,370
an error downloading, it would have got

387
00:15:40,370 --> 00:15:43,470
some form of error and we haven't, in this case.

388
00:15:43,470 --> 00:15:46,102
We also logged the number of bytes received.

389
00:15:46,102 --> 00:15:49,570
You can see we received 61601 bytes,

390
00:15:49,570 --> 00:15:52,910
which is about 6k, close to 7k,

391
00:15:52,910 --> 00:15:54,790
showing in the log so that's good.

392
00:15:54,790 --> 00:15:56,740
Obviously it's not all been logged

393
00:15:56,740 --> 00:15:58,920
but it has been downloaded.

394
00:15:58,920 --> 00:16:00,390
By the way, we can see what happens

395
00:16:00,390 --> 00:16:02,100
when things don't work properly.

396
00:16:02,100 --> 00:16:03,210
It's very simple to do, we can just

397
00:16:03,210 --> 00:16:05,880
change the URL to something invalid.

398
00:16:05,880 --> 00:16:08,000
If we close the manifest file now

399
00:16:08,000 --> 00:16:10,390
and just go back up to the top of our file

400
00:16:10,390 --> 00:16:12,950
and we'll just perhaps add another letter.

401
00:16:12,950 --> 00:16:17,820
This axe, let's add ere there to make that invalid.

402
00:16:17,820 --> 00:16:19,173
If we run that again now,

403
00:16:24,300 --> 00:16:26,120
you can see we get a completely different error here.

404
00:16:26,120 --> 00:16:30,010
Unable to resolve host aerex.itunes.apple.com.

405
00:16:30,010 --> 00:16:32,500
We get a traditional error, so basically

406
00:16:32,500 --> 00:16:35,370
it's an IO exception that's being logged there.

407
00:16:35,370 --> 00:16:37,450
We know that because it's IO exception

408
00:16:37,450 --> 00:16:39,210
reading data, which was the message

409
00:16:39,210 --> 00:16:41,820
that we typed in when we specified

410
00:16:41,820 --> 00:16:44,820
the catch block for the IO exception.

411
00:16:44,820 --> 00:16:47,720
You can see here, IO exception reading data.

412
00:16:47,720 --> 00:16:49,460
Now, the extra bit of the error message there,

413
00:16:49,460 --> 00:16:51,220
if we scroll over and have a look.

414
00:16:51,220 --> 00:16:53,420
Unable to resolve host, obviously that's not

415
00:16:53,420 --> 00:16:54,800
something that's come from us,

416
00:16:54,800 --> 00:16:57,750
that's come from this e.message property

417
00:16:57,750 --> 00:16:59,010
over here to the right hand side,

418
00:16:59,010 --> 00:17:00,900
and it's been printed out and basically

419
00:17:00,900 --> 00:17:02,810
we're impending that to the log entry.

420
00:17:02,810 --> 00:17:05,770
Exceptions include various bits of information

421
00:17:05,770 --> 00:17:08,050
and the message is a useful thing to log

422
00:17:08,050 --> 00:17:09,490
because it provides more information

423
00:17:09,490 --> 00:17:11,589
on what may have caused the error.

424
00:17:11,589 --> 00:17:12,810
Alright, so I've now tested that

425
00:17:12,810 --> 00:17:14,869
all three exceptions are caught

426
00:17:14,869 --> 00:17:17,020
but there's one thing more to do.

427
00:17:17,020 --> 00:17:19,200
Firstly, I'm gonna fix line 23.

428
00:17:21,346 --> 00:17:23,030
We're gonna undo that so we're

429
00:17:23,030 --> 00:17:25,317
left with now a valid URL again.

430
00:17:27,067 --> 00:17:28,339
Then what I'm gonna do is turn off

431
00:17:28,339 --> 00:17:30,653
the Internet connection in the emulator.

432
00:17:31,870 --> 00:17:33,993
I'm going to just bring the emulator on the screen.

433
00:17:35,020 --> 00:17:36,400
What I'm gonna do now is turn off

434
00:17:36,400 --> 00:17:38,972
the Internet connection in the emulator.

435
00:17:38,972 --> 00:17:40,700
Unlike a real device where you could just

436
00:17:40,700 --> 00:17:43,040
stop the wifi and mobile data,

437
00:17:43,040 --> 00:17:45,285
you can't actually do that on some emulators.

438
00:17:45,285 --> 00:17:48,300
What we can do though is turn on aeroplane mode,

439
00:17:48,300 --> 00:17:51,370
which prevents the emulator from accessing the network.

440
00:17:51,370 --> 00:17:52,650
Just like a physical device,

441
00:17:52,650 --> 00:17:55,030
you can drag the top of the screen down.

442
00:17:55,030 --> 00:17:58,050
We can do that here to see the common options

443
00:17:58,050 --> 00:17:59,750
but we can also go into settings if we want

444
00:17:59,750 --> 00:18:02,670
and turn on aeroplane mode from there.

445
00:18:02,670 --> 00:18:04,340
Click on that if we wanted to and

446
00:18:04,340 --> 00:18:09,340
we can do a search for aeroplane, select that.

447
00:18:11,141 --> 00:18:13,468
I'm going to turn aeroplane mode on

448
00:18:13,468 --> 00:18:16,420
and so you get the icon at the top of the screen here.

449
00:18:16,420 --> 00:18:18,900
While I'm in there, notice that wifi is off

450
00:18:18,900 --> 00:18:19,870
and that's because the emulator

451
00:18:19,870 --> 00:18:22,370
is using the computer's network connection.

452
00:18:22,370 --> 00:18:23,720
Instead what it does, it sees it

453
00:18:23,720 --> 00:18:25,980
as a mobile data connection.

454
00:18:25,980 --> 00:18:28,940
Mobile data has got an icon on the far left

455
00:18:28,940 --> 00:18:30,490
if we go back to where we were.

456
00:18:32,920 --> 00:18:36,180
I'll just close that down and bring this out again.

457
00:18:36,180 --> 00:18:39,280
We can see over here this is the option

458
00:18:39,280 --> 00:18:41,370
for mobile data connection.

459
00:18:41,370 --> 00:18:43,174
If you click on that it'll click it off

460
00:18:43,174 --> 00:18:44,294
but we're in aeroplane mode.

461
00:18:44,294 --> 00:18:45,440
I'm gonna click it off in any event.

462
00:18:45,440 --> 00:18:48,160
We're gonna leave aeroplane mode on for now

463
00:18:48,160 --> 00:18:49,537
and we come back here and run again.

464
00:18:49,537 --> 00:18:51,100
I'm gonna clear the Logcat just to

465
00:18:51,100 --> 00:18:53,370
get into the habit of doing that.

466
00:18:53,370 --> 00:18:56,500
Let's see what happens with aeroplane mode on

467
00:18:56,500 --> 00:18:58,243
and mobile data turned off.

468
00:19:02,270 --> 00:19:03,620
You can see here we got the error,

469
00:19:03,620 --> 00:19:07,410
IO exception reading data unable to resolve a host.

470
00:19:07,410 --> 00:19:08,530
Without access to the network,

471
00:19:08,530 --> 00:19:12,830
the host then can't be resolved even with a valid URL.

472
00:19:12,830 --> 00:19:15,660
Now, strangely, occasionally you will find

473
00:19:15,660 --> 00:19:17,230
this emulator will work even though

474
00:19:17,230 --> 00:19:18,980
you've set to aeroplane mode.

475
00:19:18,980 --> 00:19:20,640
If that happens, just stop the app and re-run it.

476
00:19:20,640 --> 00:19:21,870
I presume it's some sort of bug,

477
00:19:21,870 --> 00:19:24,308
perhaps with the emulator, but in our case

478
00:19:24,308 --> 00:19:26,220
you can see that it worked here OK.

479
00:19:26,220 --> 00:19:28,740
That's our app downloading the XML for the RSS feed.

480
00:19:28,740 --> 00:19:31,520
What I will do is before we change anything

481
00:19:31,520 --> 00:19:34,090
is just turn aeroplane mode off

482
00:19:34,090 --> 00:19:36,259
and click on to make sure that

483
00:19:36,259 --> 00:19:38,550
my mobile data connection is activated.

484
00:19:38,550 --> 00:19:40,323
We'll just go back and run the app one more time

485
00:19:40,323 --> 00:19:42,853
just to make sure that it is now working again.

486
00:19:47,140 --> 00:19:48,510
You can see we're now getting data

487
00:19:48,510 --> 00:19:51,770
in the Logcat down at the bottom so we're good to go.

488
00:19:51,770 --> 00:19:53,530
Alright, so that's the app downloading

489
00:19:53,530 --> 00:19:55,500
the XML for the RSS feed.

490
00:19:55,500 --> 00:19:57,020
In the next video, we're gonna change

491
00:19:57,020 --> 00:19:58,240
all this code and write it

492
00:19:58,240 --> 00:20:00,610
in a much more Kotlin-like manner,

493
00:20:00,610 --> 00:20:02,310
so I'll see you in the next video.

