67: Dealing with Old Code
00:00:00
◼
►
Welcome to Under the Radar, a show about independent iOS app development.
00:00:03
◼
►
I'm Mark Orment.
00:00:04
◼
►
>> And I'm David Smith.
00:00:06
◼
►
Under the Radar is never longer than 30 minutes, so let's get started.
00:00:10
◼
►
So today we are going to be talking about old code.
00:00:15
◼
►
And the idea for today's discussion got started from some work I've been doing recently,
00:00:20
◼
►
updating and fixing some issues in one of my apps.
00:00:23
◼
►
It was actually the first app that I had that ever really was in any reasonable way a success.
00:00:28
◼
►
It's an app called Audiobooks that lets you listen to public domain audiobook recordings.
00:00:34
◼
►
And I launched it in spring of 2009.
00:00:39
◼
►
So it's coming up on its eighth birthday today.
00:00:44
◼
►
And it's kind of a wild thing to be going through and working -- I'm still actively
00:00:50
◼
►
working on it for the last eight years.
00:00:52
◼
►
I've had continuous updates, and it launched at a time when there was one screen size.
00:00:58
◼
►
And that screen size was non-retina.
00:00:59
◼
►
We were doing retain and release.
00:01:03
◼
►
All of the buttons are super shiny.
00:01:05
◼
►
They have that really round kind of capsule look to them.
00:01:10
◼
►
And it even has some features that I look at now, and it took me a while to remember
00:01:14
◼
►
why I added them.
00:01:16
◼
►
For example, it has a feature where you can automatically resume playback of the audio
00:01:21
◼
►
when the app starts up.
00:01:23
◼
►
And that's because the app was created before multitasking was a thing, where when you close
00:01:28
◼
►
the app, it would stop playing.
00:01:31
◼
►
And so I made it so that as soon as you start it back up, you could resume to make it a
00:01:37
◼
►
little bit easier for that.
00:01:38
◼
►
But the app is so old that it has all of these code paths and these details.
00:01:45
◼
►
There's sections of the code where it says, "Is multitasking supported?
00:01:50
◼
►
If not, do that."
00:01:51
◼
►
And multitasking has been available since iOS 4.
00:01:54
◼
►
>> Enoch: And if I'm doing my timeline correctly, it looks like you launched this when the current
00:01:58
◼
►
version of iOS was still 2.0.
00:02:23
◼
►
The thing that's been making me think about, though, is I'm doing this process of doing
00:02:41
◼
►
this big spring cleaning for this app.
00:02:44
◼
►
And it creates all these weird questions, though, like how to deal with all this old
00:02:49
◼
►
code, all this old stuff, and there's all this legacy weight that goes into this app.
00:02:54
◼
►
And it's theoretically possible that there's a customer out there who has been using the
00:03:00
◼
►
app since 2009 continuously.
00:03:04
◼
►
And so there's all these interesting cases and details that I have to manage and deal
00:03:08
◼
►
with because, for example, they may have had data in their database that is from the original
00:03:16
◼
►
version, and I have a whole bunch of code in my app to translate old versions of, you
00:03:22
◼
►
know, I think I've gone through three or four database formats or things.
00:03:25
◼
►
Like originally I launched and the database was a plist, I think.
00:03:31
◼
►
>> When you launched, core data was not yet on the phone.
00:03:34
◼
►
You could do raw SQLite through the C API, but most people just had these weird little
00:03:39
◼
►
hacks like plists or very, very basic SQLite functionality because it was so cumbersome.
00:03:46
◼
►
>> Yeah, exactly.
00:03:48
◼
►
It was a plist to start with, and then I transitioned to core data, and then core data has gone
00:03:53
◼
►
through several migrations.
00:03:54
◼
►
And so it's a lot of these weird, complicated issues that I feel like you don't -- when
00:04:01
◼
►
I'm building things now, I don't really think about this kind of future-proofing and migration
00:04:04
◼
►
and translation and the things that I may need to do if the app is sitting around.
00:04:09
◼
►
I don't know if you think about this when you're doing overcast stuff, that like what's
00:04:13
◼
►
going to happen if someone who's been running the old version for years and years and then
00:04:20
◼
►
suddenly installs the new version?
00:04:21
◼
►
It could have a totally different database scheme.
00:04:23
◼
►
It could have a totally different file format.
00:04:26
◼
►
All the MP3s could be in a different place.
00:04:29
◼
►
Time is a weird thing with software, I think.
00:04:32
◼
►
>> Yeah, I mean, I've avoided many of the -- I mean, first of all, my migrations for
00:04:37
◼
►
the database are all fairly straightforward.
00:04:40
◼
►
I do have a lot of that code that can support old versions.
00:04:43
◼
►
However, in practice, I don't have a lot of people using old versions because from day
00:04:47
◼
►
one I decided to use SSL certificate pinning on my connection to my API.
00:04:52
◼
►
And this has caused -- it's a nice thing for security.
00:04:56
◼
►
However, at various points I've tried pinning two various things.
00:05:00
◼
►
First I pinned to the certificate itself, which only lasted until that SSL certificate
00:05:05
◼
►
expired, which was about a year.
00:05:08
◼
►
And then I realized, well, it's kind of inconvenient to break all the old versions of my app every
00:05:11
◼
►
time I have to update my SSL certificate on my server.
00:05:15
◼
►
So I tried pinning to the intermediate certificate through my SSL issuer, figuring, well, that
00:05:19
◼
►
won't change for a long time until it expires in like five years.
00:05:23
◼
►
And then all the encryption standards got upgraded to, I think, SHA-256 or somehow they
00:05:29
◼
►
changed the signature algorithms to be more secure on all certificates.
00:05:32
◼
►
And so that broke.
00:05:33
◼
►
And so I had that force an upgrade.
00:05:35
◼
►
And then on my most recent one, just a few weeks ago, I updated my certificate.
00:05:41
◼
►
And I'm like, oh, I'll be fine.
00:05:42
◼
►
I'm pinned to the new SHA-256 intermediate certificate.
00:05:45
◼
►
I can update and it'll be fine.
00:05:47
◼
►
But then the new certificate I got just was signed with a different intermediate key.
00:05:52
◼
►
Like for whatever reason, like, OK, that's not good.
00:05:57
◼
►
So I had to forcibly break all previous clients who connect.
00:06:01
◼
►
And I gave like a month notice and I let it go for a while.
00:06:05
◼
►
But then like the actual expiration date on the old certificate was actually as we record
00:06:12
◼
►
And so I was forced to break all compatibility with all old versions yesterday, basically.
00:06:21
◼
►
So I don't really have that problem as much.
00:06:25
◼
►
And this kind of gives me a lot of advantages.
00:06:27
◼
►
I mean, one advantage is that I don't have to really worry about supporting old versions
00:06:31
◼
►
of the OS very much.
00:06:32
◼
►
It's like, well, even though it's inconvenient that I had to force all these people to update
00:06:36
◼
►
the latest version, that also means that I literally have zero people using anything
00:06:41
◼
►
older than it.
00:06:43
◼
►
So it simplifies a lot of this stuff.
00:06:47
◼
►
And I've found that usually people who are running very, very, very old versions of things,
00:06:53
◼
►
they kind of expect things to break if they ever update them.
00:06:56
◼
►
That's one of the reasons that they aren't updating them, because either they can't or
00:07:00
◼
►
And the reasons why they can't or won't are usually because either their hardware doesn't
00:07:03
◼
►
support anything new, or in which case you're fine, because any new installation will be
00:07:07
◼
►
on new hardware.
00:07:08
◼
►
Or that they refuse to update for whatever reason.
00:07:12
◼
►
Maybe they just don't like the new OS.
00:07:13
◼
►
Maybe they think it'll run too slowly on their hardware.
00:07:15
◼
►
Maybe they have a jailbreak they want to preserve.
00:07:16
◼
►
Whatever the case is, they refuse to update.
00:07:19
◼
►
In which case, I feel like if you are refusing to update to something that you could update
00:07:23
◼
►
to, I kind of feel like you're taking matters into your own hands and accepting the responsibility
00:07:27
◼
►
of things might be weird for you holding onto old stuff.
00:07:31
◼
►
And one of the ways things might be weird is you might have some kind of failed migration
00:07:35
◼
►
in the future when you do decide to upgrade, when you're upgrading way after everyone else
00:07:40
◼
►
So for the most part, the issue of migrating old data over time and everything is, I think,
00:07:47
◼
►
not that big of a deal in practice.
00:07:49
◼
►
You should do it as much as you can.
00:07:51
◼
►
You should accommodate that, but not to the point where it's going to become a large burden
00:07:55
◼
►
on you while you should be supporting new customers, basically.
00:08:00
◼
►
And I think it certainly is complicated, especially for apps that, like Overcast, it requires the
00:08:06
◼
►
server for it to function, period.
00:08:09
◼
►
And so it doesn't have the sense of an offline or a standalone kind of feeling.
00:08:15
◼
►
Where this app, my audiobooks app, it still works.
00:08:19
◼
►
I actually, out of curiosity yesterday, I exported version one out of my Git repository
00:08:26
◼
►
and got it to run in the most recent version of Xcode, which surprisingly worked surprisingly
00:08:33
◼
►
well given how much time has passed between those things.
00:08:37
◼
►
>> That's kind of impressive.
00:08:38
◼
►
>> I only had to fix a few bugs and set the root view controller on the window and a few
00:08:43
◼
►
things that otherwise it just wouldn't launch.
00:08:45
◼
►
But overall, it ran.
00:08:47
◼
►
And the app still works because it was built at a time when it needed to be standalone
00:08:55
◼
►
because network connections were super flaky and everyone was on edge or 3G at the time.
00:09:01
◼
►
And it was a very different paradigm.
00:09:03
◼
►
So the app was very standalone.
00:09:05
◼
►
And I think any app that has that kind of standalone-ness to it is where it really gets
00:09:09
◼
►
complicated for these kinds of data formats and migration kind of stuff.
00:09:15
◼
►
What I'm struggling with now as I go through this is the issue you run into is you end
00:09:20
◼
►
up with this kind of Russian doll data format where I have code in the app that lets me
00:09:29
◼
►
migrate -- every little migration or thing that I've done over time, I have code to manage
00:09:36
◼
►
from one to the next to the next to the next.
00:09:38
◼
►
And so there is a path that if I took something that was running that very first version,
00:09:44
◼
►
I think there's -- maybe not that very first one, but definitely the core data versions.
00:09:49
◼
►
Theoretically, if you had a device that was running that and then you reinstall the latest
00:09:53
◼
►
version, it would go through six different migrations.
00:09:57
◼
►
It would migrate this format change, then this format change, then this format change.
00:10:02
◼
►
And it's a really tricky thing, though, for me as I'm going through this code.
00:10:07
◼
►
I have no idea if this works still.
00:10:10
◼
►
But it's still there in the code that if you were running database version 2, that
00:10:14
◼
►
I have this code that says if you're 2, I can get you to 3, and then there's code from
00:10:17
◼
►
like 3 to 4.
00:10:19
◼
►
But that sounds horribly error-prone and unlikely to actually work in practice.
00:10:24
◼
►
And so what I'm trying to go through now is should I just be deleting some of these old
00:10:29
◼
►
Should I just be going through and saying I'm supporting migration from whatever the
00:10:34
◼
►
last major version to the current version and then cutting it off there?
00:10:39
◼
►
Because it's a really -- theoretically, if I'm having this code in there that's doing
00:10:43
◼
►
something, I should probably be able to -- I should probably have a way to reliably ensure
00:10:49
◼
►
that it works.
00:10:51
◼
►
And I don't know if that's actually a guarantee that I want to make.
00:10:55
◼
►
>> Yeah, I mean, like, you know, on one hand, you could just do what you just did and check
00:10:59
◼
►
out version 1.0 out of Git and build it and put some data in there and then check out
00:11:04
◼
►
the current head version and run it and see if everything gets migrated over.
00:11:08
◼
►
But again, I think as indie developers, there's so much stuff where like, well, it would be
00:11:14
◼
►
nice if we had the time to do X, Y, or Z.
00:11:16
◼
►
Or it would be nice if we had enough staff and resources to do X, Y, or Z.
00:11:20
◼
►
But in reality, you have to prioritize.
00:11:22
◼
►
And it is probably not worth a lot of effort to maintain these code paths that are going
00:11:30
◼
►
to support somewhere between like 0 and 10 people ever.
00:11:35
◼
►
You know, like it's not like a huge deal.
00:11:37
◼
►
So basically, like the way I come down on it is, you know, what I said earlier, it's
00:11:41
◼
►
like if it's going to be really easy to keep the support in, like if you have a couple
00:11:46
◼
►
of instructions to migrate databases forward, like I don't see the value in deleting them
00:11:51
◼
►
necessarily because, you know, that isn't that much code and it's not really hurting
00:11:55
◼
►
anything to be there.
00:11:56
◼
►
But I, you know, but if it becomes a burden, if for whatever reason that is causing you
00:12:01
◼
►
to not be able to upgrade to something else or clean up something else or not be able
00:12:07
◼
►
to change the app in a way that would benefit all current and new customers, then I think,
00:12:14
◼
►
you know, then the cost is too great to having those and then you should get rid of them.
00:12:17
◼
►
But I also don't think it's going to be worth your time to routinely check out version
00:12:23
◼
►
1.0 and get some data and then check out the head.
00:12:27
◼
►
To test these migrations that far back where you might literally be the only person who's
00:12:32
◼
►
ever doing that, then it's probably not worth the time taken away from doing things
00:12:38
◼
►
that benefit everybody.
00:12:39
◼
►
Yeah, and I mean I think in a similar way I've been also working through some of these
00:12:43
◼
►
thoughts about dealing with like just old device styles and types too.
00:12:49
◼
►
Like for example, I still have all non-retina assets in the app.
00:12:56
◼
►
Which is a funny thing because on the iPad, does iOS 10 have a non-retina iPad that it
00:13:03
◼
►
still supports?
00:13:04
◼
►
No, because even the iPad 3 it got dropped.
00:13:07
◼
►
But it is, I think 9 still supported iPad 2 and 3 I think.
00:13:12
◼
►
Yeah, and so it is funny when I have all these resources, especially if they're iPhone only,
00:13:17
◼
►
like these are resources that can never be seen.
00:13:21
◼
►
And so I'm going through and being like, "Should I clear this up?
00:13:24
◼
►
It'll make my bundle a little bit smaller to just have 2x and 3x assets."
00:13:30
◼
►
And I mean on the iPad it's especially interesting because for me and my use, something like
00:13:36
◼
►
45% of the iPad users who use audiobooks are doing it on a device that doesn't support
00:13:44
◼
►
Like mostly the iPad 2 and the iPad mini.
00:13:47
◼
►
That's a lot.
00:13:49
◼
►
Yeah, which makes up, I mean I imagine it's the nature of the, I mean the app's just been
00:13:53
◼
►
around for a long time and that's active use too.
00:13:56
◼
►
It's not just like total install.
00:13:58
◼
►
Because I can imagine it's a lot of people who have an iPad that they just load audiobooks
00:14:02
◼
►
on and listen to in their kitchen or on their bedside when they're going to bed or something
00:14:11
◼
►
It seems like it's that kind of a device.
00:14:12
◼
►
And so it's tricky when I have these devices that, I think right now I support iOS 8, 9,
00:14:20
◼
►
and 10, or is my official support, and with this update I'll probably be going to 9 and
00:14:26
◼
►
But one thing that I've definitely run into a few times is dealing with these, is the
00:14:30
◼
►
issue of a device that just can't get the latest version of the app, period.
00:14:35
◼
►
And I think this is, with the iPads especially, this is going to be more notable than it is
00:14:41
◼
►
for iPhones.
00:14:42
◼
►
Because I just think iPhones don't stick around as long.
00:14:45
◼
►
Like there's very few people using an iPhone 4 or an iPhone 3GS these days.
00:14:51
◼
►
And so it's something that I worry about less.
00:14:54
◼
►
Though I will say one little trick that I always do, I've started doing in all my apps
00:14:59
◼
►
just like for, it's saved me so many times, is I always enable the iTunes file sharing
00:15:08
◼
►
setting in most of my apps.
00:15:12
◼
►
And it's mostly because it's like, I came into it most usefully for my recipe app, where
00:15:18
◼
►
it has people store their recipes and the images and all these associated assets for
00:15:26
◼
►
the recipe collection.
00:15:27
◼
►
And it's nice to have a method that if someone emails me and says, I get this a lot, is I
00:15:32
◼
►
have a first gen iPad, like my recipe book launched day one, or pretty soon after that,
00:15:38
◼
►
of the original iPad.
00:15:39
◼
►
And there are people who've been using it just like they take that iPad, they put it
00:15:42
◼
►
in their kitchen, and they never changed it.
00:15:43
◼
►
And they've been using it ever since.
00:15:46
◼
►
And that version of the iPad is so unsupported by iOS versions, by versions of the app, that
00:15:54
◼
►
it was really awkward to be like, well, there's not much that I can do to help you.
00:16:00
◼
►
And so what I ended up saying is I enabled that iTunes file sharing.
00:16:03
◼
►
And then at least what I can say to these people is, hook it up to iTunes, grab these
00:16:07
◼
►
files, put them on your desktop, drag them back onto your new iPad, because usually that's
00:16:11
◼
►
the situation they find themselves in.
00:16:13
◼
►
It's like, I got a new iPad, yay, but what do I do?
00:16:15
◼
►
And it's like they can then, at the very least, take those database files and move them back
00:16:20
◼
►
And then, like I was just saying, I have all the Russian doll migration scripting so that
00:16:25
◼
►
it can take those first early versions of the app and make them move forward.
00:16:30
◼
►
But if I hadn't enabled the iTunes file sharing API back then, they would just be stuck.
00:16:37
◼
►
There'd be no way to get those files realistically out of the device.
00:16:40
◼
►
They'd have to use some kind of iPhone Explorer specific tool.
00:16:45
◼
►
Download Phone View.
00:16:46
◼
►
Yeah, download Phone View and migrate, which is never going to happen.
00:16:49
◼
►
But at least iTunes.
00:16:50
◼
►
I think if step one of your troubleshooting is download Phone View, you're probably not
00:16:55
◼
►
going to be successful with that.
00:16:58
◼
►
So at least that is a little hint that I now just do it out of course, because I think
00:17:02
◼
►
most people don't know it's there, and so it's unlikely to be dangerous.
00:17:07
◼
►
Somehow people are going to be like, oh, what can I do with these files?
00:17:09
◼
►
And start randomly deleting their databases.
00:17:12
◼
►
But every now and then, it really comes in handy for somebody who's like, how do I move
00:17:17
◼
►
my files from this phone to this phone?
00:17:20
◼
►
Or it's even the common one that I get now with like, in pedometer, people are like,
00:17:24
◼
►
I have all my steps on this device, and I don't want to do backup and restore, or it's
00:17:29
◼
►
too old to do backup and restore because the versions are incompatible.
00:17:32
◼
►
What can I do?
00:17:33
◼
►
And it's like, well, go to iTunes.
00:17:35
◼
►
It's awkward, but you just write out a big customer support guide that says click here,
00:17:41
◼
►
click here, click here, and then it works well enough.
00:17:44
◼
►
All right, we are sponsored this week by Linode.
00:17:47
◼
►
Linode servers offer industry-leading performance with native SSD storage, Intel E5 Xeons, and
00:17:54
◼
►
access to a 40-gigabit network.
00:17:56
◼
►
They have nine data centers spread across the world, which give you the ability to serve
00:17:59
◼
►
your customers quickly.
00:18:01
◼
►
And Linode's API allows you to easily automate tasks or develop custom applications in the
00:18:05
◼
►
cloud with super simple scaling.
00:18:08
◼
►
This allows you to resize your servers in just a couple of clicks.
00:18:10
◼
►
I've done this myself many times.
00:18:11
◼
►
It's been awesome.
00:18:12
◼
►
In fact, I'm actually doing one later today.
00:18:13
◼
►
I'm running out of disk space on my backup server.
00:18:15
◼
►
I'm going to just go and resize it later today.
00:18:16
◼
►
It's going to take about 10 minutes, most of which I'm just waiting for it to complete,
00:18:19
◼
►
and it's going to be great.
00:18:20
◼
►
I've done it so many times.
00:18:21
◼
►
I know exactly how it's going to go, and man, I love Linode.
00:18:24
◼
►
And all of this is also manageable if you want via the command line through their API
00:18:27
◼
►
as well, if you don't want to use their interface or if you want to automate large tasks.
00:18:31
◼
►
All of Linode's pricing tiers feature hourly billing with monthly caps on all plans and
00:18:35
◼
►
add-on services like backups and node balancers.
00:18:39
◼
►
So Linode, they also have some awesome new pricing options.
00:18:42
◼
►
You can now get a server with one gig of RAM for just five bucks a month.
00:18:48
◼
►
I can't believe how cheap servers are.
00:18:51
◼
►
This makes me so happy because servers used to be so expensive.
00:18:54
◼
►
And when I was starting out, the idea of five bucks a month for a server with a gig of RAM,
00:18:59
◼
►
oh my god, I paid so much more for so much less back then, and you can go all the way
00:19:02
◼
►
up to 16 gigs of RAM for only 60 bucks a month.
00:19:06
◼
►
Oh man, their prices are good.
00:19:09
◼
►
And their two gig plan now includes 30 gigs of storage, and that's just 10 bucks a month
00:19:14
◼
►
for two gigs of RAM, 30 gigs of SSD storage.
00:19:17
◼
►
Linode continues to offer more and more awesome options to meet your server needs.
00:19:21
◼
►
Across the board, they're offering twice the amount of RAM that you get elsewhere.
00:19:25
◼
►
As listener of this show, if you sign up at linode.com/radar, you'll not only be supporting
00:19:30
◼
►
us but you'll also get $20 towards any Linode plan, and with a seven-day money-back guarantee,
00:19:35
◼
►
there's nothing to lose.
00:19:36
◼
►
So go to linode.com/radar to learn more, sign up and take advantage of that $20 credit or
00:19:41
◼
►
use the promo code radar2017, that's radar2017, just like the year, I hope, at checkout.
00:19:48
◼
►
Thank you so much to Linode for supporting this show.
00:19:50
◼
►
All right, and the next area that I've been recently battling through with the same app
00:19:56
◼
►
that I think is interesting to talk about is the concept of iOS deprecation.
00:20:03
◼
►
So the app when I launched it, when I started this project, came up, I think there was something
00:20:08
◼
►
on the order of 80 deprecation warnings, which is certainly an indication of my, I guess,
00:20:17
◼
►
ability to keep on top of things.
00:20:21
◼
►
My favorite was I had one deprecation warning that said, I think it had something to do
00:20:25
◼
►
with the audio session APIs, and it was the set delegate method, and it said, "This method
00:20:30
◼
►
was first deprecated in iOS 6."
00:20:34
◼
►
So I'm a little behind, and it's amazing that Apple has been very kind to me, and they deprecated
00:20:41
◼
►
it in iOS 6, and it still continues to work just fine in iOS 10, but deprecation is probably
00:20:48
◼
►
worth just saying briefly what I'm talking about.
00:20:50
◼
►
So this is the, Apple will take a particular API, a particular method, and say, "We are
00:20:58
◼
►
deprecating this method," which means we have something new or we have something different
00:21:02
◼
►
that we want you to use, and usually the deprecation warning will even be nice enough to say, "You
00:21:06
◼
►
shouldn't be using this method anymore.
00:21:08
◼
►
You should be using this one," and point to it.
00:21:12
◼
►
And what they're saying is, at some point, indistinctly in the future, this method is
00:21:17
◼
►
going to go away, or it'll stop working correctly, or whatever, and this is their polite way
00:21:22
◼
►
of saying, "You need to change your code to work with the new stuff."
00:21:31
◼
►
Deprecation I feel like is one of these funny things where it reminds me a lot of the Hemingway
00:21:35
◼
►
quote about going bankrupt, where you go bankrupt two ways.
00:21:39
◼
►
You go bankrupt gradually, and then suddenly, because that's essentially what the deprecation
00:21:44
◼
►
warnings are.
00:21:45
◼
►
You very gradually have this building up, like I have these deprecation warnings that
00:21:48
◼
►
have been building up over time, and they're like, "I should be changing things.
00:21:51
◼
►
I should be improving things," and then one day suddenly, it'll just stop working.
00:21:55
◼
►
iOS 11 will come out this June, and then suddenly I no longer have the choice and the flexibility
00:22:00
◼
►
and the ability to just like, "Oh, I'll get to that whenever I want to."
00:22:05
◼
►
It's like, "No, suddenly I have to do it.
00:22:07
◼
►
The app will no longer compile."
00:22:11
◼
►
So it's a really tricky thing, though, because the thing that I always struggle with with
00:22:15
◼
►
deprecation is it's the issue of when to do it, because the code works as it is right
00:22:24
◼
►
And that is one of the hardest things, I think, for me to be able to justify and work, is
00:22:29
◼
►
I'm working on an app.
00:22:30
◼
►
Here's this function that works correctly, like functionally has been tested, has been
00:22:35
◼
►
out in customer hands for, in this case, for years and years, and it works, it's reliable,
00:22:41
◼
►
all the bugs have been worked out.
00:22:42
◼
►
For me to come along and to change it when it is working now always feels a little bit
00:22:50
◼
►
And while I know that it's a bad thing to not, in theory, or I should probably be doing,
00:22:55
◼
►
is as soon as I see a deprecation warning, I need to be going in there, changing it right
00:22:59
◼
►
at that very moment.
00:23:01
◼
►
But at the same time, APIs are most buggy when they're new, and there's lots of other considerations
00:23:07
◼
►
that come into that that mean that sometimes I want to wait, but at the same time I don't
00:23:12
◼
►
want to end up completely bankrupt at the end, where suddenly I'd have no choice and
00:23:15
◼
►
I have to change everything at once, and then I'm changing, it's even more dangerous than
00:23:19
◼
►
changing little things along the way as probably changing 80 warnings as I am right now.
00:23:25
◼
►
That's a bit more problematic.
00:23:26
◼
►
But that balance and that tension, I find, is really awkward and complicated to deal
00:23:31
◼
►
- I mean, the way I deal with deprecation is kind of like what I was saying last week
00:23:35
◼
►
about Swift adoption, which is like, it's the kind of thing where a deprecation is basically
00:23:42
◼
►
a note, it's adding something to your to-do list, that you're going to need to deal with
00:23:47
◼
►
And like most to-do items, I think practitioners of GCD and similar systems, there's almost
00:23:53
◼
►
always a rule in those systems that says something along the lines of, if you can do something
00:23:58
◼
►
really quickly, just do it right now and just get it done.
00:24:01
◼
►
And if not, then you schedule it and prioritize whatever else.
00:24:04
◼
►
Sorry, I'm not an expert in those systems, but I know there's usually the rule that says
00:24:08
◼
►
if it's easy, just do it now.
00:24:10
◼
►
And that's kind of how I look at deprecations and things like new languages, new APIs, new
00:24:17
◼
►
frameworks, that the easy stuff, deprecations are usually really easy to get around.
00:24:22
◼
►
Usually it's like, oh, there's now a new method that has an options parameter or a callback
00:24:26
◼
►
or something else, it's like, usually the way to deal with it is very quick, you can
00:24:31
◼
►
do it in a couple minutes at most and you're done and then that's it.
00:24:35
◼
►
And the problem, as you said, it's like, similar to what I was saying last week about Swift,
00:24:38
◼
►
about like, you know, at some point in the future there's going to be some API or some
00:24:42
◼
►
policy or something that requires Swift and then like I'll be forced to learn it right
00:24:47
◼
►
then, which is kind of not on my own time, not on my own schedule.
00:24:51
◼
►
And it's similar with deprecations, like at some point you're going to be forced to do
00:24:55
◼
►
this and so you're better off doing it when you have time on your own terms, on your own
00:25:01
◼
►
schedule as opposed to in the future being forced suddenly, you know, oh, now I need
00:25:06
◼
►
to do this instead of what I was supposed to be doing today.
00:25:09
◼
►
It can also happen with app review, like there could be a time where you need to submit a
00:25:13
◼
►
critical bug fix to your app and that happened to be the day that they started enforcing
00:25:22
◼
►
this particular deprecation warning that you're hitting in app review and all of a sudden
00:25:25
◼
►
now you can't even submit this bug fix that you need to submit because you can't submit
00:25:29
◼
►
anything until you fix this deprecation.
00:25:31
◼
►
And so it's a kind of thing where like most deprecations are easy to fix.
00:25:35
◼
►
If you can fix it, just do it now because there will never be a good time later to do
00:25:40
◼
►
>> Yeah, and I think the only thing that's also complicating into this is the broader
00:25:45
◼
►
the range of iOS versions that you support, the more complicated this becomes, I think.
00:25:51
◼
►
>> That's true, yeah, that's true.
00:25:52
◼
►
>> Because one of the things, like part of the reason why this app has such a wide range
00:25:57
◼
►
of deprecation warnings is, you know, a lot of them were when I changed the minimum supported
00:26:02
◼
►
version from iOS 8 to iOS 9, you know, then suddenly all the things that were deprecated
00:26:07
◼
►
in iOS 8 become deprecated because before that they weren't deprecated.
00:26:11
◼
►
In fact, they were essential because if I installed the app on a device that runs iOS
00:26:17
◼
►
8 and used the new API, it won't know anything about it and it won't work.
00:26:22
◼
►
And so like this is something too that it's probably worth keeping in mind.
00:26:27
◼
►
Like I think something that I've learned from this experience is that even if I'm not dropping
00:26:31
◼
►
support for the older version right away, like when iOS 11 comes out this June presumably,
00:26:39
◼
►
I'm unlikely to drop support for it right away for this particular app.
00:26:42
◼
►
For some of them I might, but for this one I probably won't.
00:26:45
◼
►
What I probably should do though is set the minimum version to iOS 11 and see what is
00:26:52
◼
►
deprecated as a result, to get a sense of how big this hole I'm digging myself into
00:26:59
◼
►
by keeping these things around.
00:27:01
◼
►
And I mean, I will say to Apple's credit, like they are very good about this.
00:27:04
◼
►
Like it is kind of crazy to me that how much work they seem to put into backwards support
00:27:11
◼
►
and backwards compatibility, the fact that I can run a really old version using modern
00:27:17
◼
►
Xcode is quite a testament to them.
00:27:19
◼
►
And similarly, the fact that I can build, I don't know how far back I can go with the
00:27:24
◼
►
modern version of Xcode, like if I could support iOS 4 or iOS 3.
00:27:28
◼
►
I'm sure at some point Apple cuts it off, but the fact that they go back a couple versions
00:27:35
◼
►
at least and cover the vast majority of users as a result is certainly a testament to the
00:27:41
◼
►
engineering priorities and making sure that their devices, that you don't have these very
00:27:46
◼
►
abrupt and very unexpected cutoffs, which I'm sure it takes effort and time on their part,
00:27:53
◼
►
so they don't have to do that, but I'm glad that they do.
00:27:57
◼
►
And I think the last thing that I've also just been thinking about as I've been going
00:28:01
◼
►
through this is something that I notice when I'm going through these kind of cleaning passes,
00:28:06
◼
►
and going through and cleaning up something, is it's always funny when you're going through
00:28:11
◼
►
an old code base and you find methods that, like I've been noticing this when I'm, mostly
00:28:16
◼
►
when I've been fixing deprecation warnings, like I find this method that has a deprecation
00:28:19
◼
►
warning in it, I go into that method and I'm like, "Huh, I wonder where this is used."
00:28:22
◼
►
And I do like, you know, a search all for the method signature, and it's not used anywhere.
00:28:28
◼
►
Like it's kind of a funny thing where it's like there's this method that, you know, there's
00:28:33
◼
►
all this code in the app that has no references to it anywhere because it existed at some
00:28:39
◼
►
point, and then I rewrote the thing that was referencing it, and then it just sort of accumulates
00:28:45
◼
►
And I went into AppCode, which is the IDE that JetBrains put out, which is like, I don't
00:28:51
◼
►
use it for, I wouldn't ever use it for development, like I really like the way Xcode works, but
00:28:55
◼
►
it has a bunch of these kind of refactoring tools, and like I found that it said, I think
00:28:59
◼
►
there was 426 methods that were unused in the application, but it's just like, it's
00:29:04
◼
►
the nature of, it's existed since, you know, spring of 2009.
00:29:09
◼
►
And so I'm going through and cleaning this up, and I think it's, again, it's just one
00:29:12
◼
►
of these things that's reminded me of like, it's probably good as I'm going to be a bit
00:29:16
◼
►
more thoughtful about this, that when I'm removing, you know, as I'm making changes,
00:29:20
◼
►
if I'm removing the use of a function for the last time, I should probably, you know,
00:29:25
◼
►
clear it out there and remove the amount of code in my project because it's just increasing
00:29:30
◼
►
the odds that, you know, there's going to be these lingering and weird bugs.
00:29:34
◼
►
Like the less code in my app, the less bugs there are, almost certainly, so it's just
00:29:37
◼
►
like a good reminder to me that I should be cleaning things up a little bit more.
00:29:40
◼
►
All right, we're out of time this week.
00:29:42
◼
►
Thank you everybody for listening, and we'll talk to you next week.