Lecture 15. Android Services and Local IPC (parts 1 and 2)

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
so today we're going to start talking about services and we'll explain various kinds of Android services and we'll discuss these things in the context of an application that's very much like what you're doing for the next programming assignment so we'll go ahead and dive into that okay so just to give a little introduction to what we'll be covering services don't have a user interface they rely on other things to get the user interface interactions and they're most commonly used to run certain operations in the background especially long-running operations run in the background typically activities are the things that are going to be used to to invoke operations that or send requests intents to services to do the work on the behalf of the activity there's other ways of course services can communicate as well but that's one of the more common ways to do things and there's a number of very interesting inter process communication or so called IPC mechanisms that are used in order to be able to allow activities and services to talk to each other or different services to talk to each other and so on and so forth and so we're going to be talking about a lot of those topics throughout the rest of this particular module you'll see that you could talk about some of those things in isolation from services but they're so closely aligned that it really makes sense to talk about them together so we're going to spend some time talking about services and as we talk about different kinds of services you'll understand why we have a variety of different kinds of inter process communication mechanisms to interact between the different kinds of services okay so the first part of this module is going to kind of give you an overview of what a service is not unlike the discussions that we had when we were talking about the activity so this this is kind of the same parallel structure that we were using back then so a service is an Android component it's a component just like we have activities or content providers or broadcast receivers it's one of the four core components that are part of the Android application programming infrastructure or or application architecture I suppose as better term and they're used to run typically to use to run long-running operations in the background you'll see there's a whole variety of different ways to interact with services but a very common approach is to run them in the background and you can do all kinds of interesting things and services you could handle some kind of network interaction you could send request receive requests you could download a file chat we're gonna be doing here like an image you can interact with some kind of content provider on behalf of something else in the background you could run periodic tasks that have to run on the passage of time or when certain data shows up and you'll see there's lots and lots of examples of these things in our particular environment we're going to talk about for the next assignment and what we'll cover here today in the next few weeks is a download service something that downloads files on your behalf now there is an existing download service that's part of Android and so you could certainly use that but we're going to get some experience actually building a service so you can get a feeling for how it works there's a lot more information that's available on the Android website and I strongly encourage you to take a look really well-written gives you a good feeling for how it works shows you a whole bunch of examples and so on so we'll help get you up to speed if you have any questions about some of the details typically other Android components are used to start services most most commonly activities are used and one of the things that's interesting about a service is it can continue to execute in the background even if the activity that initially launched it happens to go away or if the user switches around to a different activity that service is still there on behalf of the original activity doing stuff on its be and of course there could also be system services as well things that are long-running not necessarily pegged to any particular to user activity at all their system services that do things like location service keep track of where the phone is and the radio managing communication messaging things like SMS and MMS and so on those are services that exist that kind of are there to be run when things happen in the system since the service doesn't provide a direct interaction with the user that means that you can't make calls to widgets in the context of a service you already probably knew this a little bit from our discussions we have before about things that run in the background things that running threads for example that are not the main thread but a service may or may not run in the main thread but regardless you're not you're not supposed to make calls in the service that interact with the user interface under some interesting circumstances you might be able to get away with it but you definitely want to write code that depends on this because it's very easy to change the context in which the service runs simply by modifying some of the metadata some of the Android manifest file properties and we'll look at some of those things as we get a little bit further along now the main thing we're going to talk about today and then we'll go into a little detail on one of these things is the two different types of services so in Android there's something called a started service and there's something that's called a bound service a started service is is the simpler of the two in some sense it's simpler to to program quickly although it may not be simpler to use because it has some restrictions and limitations that are not there with a bound service so a a started service is typically used to perform a single operation and oftentimes it doesn't necessarily return a result directly to the user it might you can program it using various IPC mechanisms like messages and so on to return results but it's not necessarily always the case so we'll see there's a whole pile of examples of started services we'll look at in a second a bound service in contrast is typically something that started when a client starts it up and as long as the client or clients or talking to it then it provides a way of making at server calls invocations on that service and as long as someone's bound to the service the service remains running and so you can actually carry out some kind of long duration conversation with the service that's that's launched and we'll see there's a bunch of those kinds of services as well when we get a little further along you'll see that there's a bunch of interesting patterns that are implemented by these various services and the started service implements something called the command processor pattern and the bound service implements something called the broker pattern and we'll look at both of those patterns throughout the next few weeks so how do you start a started service very simple you call start service and typically this is done by an activity and usually what happens is you create some kind of intent and you you either give a specific service that you want to invoke like the threaded download service dot class file which is kind of hard coded to one particular thing or you can you can rely on some intent filtering mechanisms that are part of the Android intents framework we'll talk about that a little bit later however you do it though you create this intent and then you go ahead and potentially add some additional things to the intent they're called extras you can put in various things like a user name URL password you know various things you might want to use to communicate from the caller or the activity to the service and then you go ahead and say start service and the Android system uses the intent together with the information the intent the the action that the intent corresponds to the data that may be in there the category of the intent all these things are factored in to allow the Android infrastructure the the so-called intense framework to figure out who's going to handle this intent and if that service isn't running then it'll Android will start the service and it will deliver the intent to that service and if you take a look there's a link here that goes to the part of the service web page that explains how you create a started service and it just kind of walks to these points we'll talk shortly about the lifecycle hook methods that are invoked here or when we got a little bit further along and we'll talk a bit more about this when you call start service on cert when you call start service and pass in an intent then once Android figures out which service is going to need to run it launches that service or if it's already running it finds out where it is and then it goes ahead and it delivers the intent to the service and it does it by calling back a predefined hook method that you're often obliged to override not always but typically is the case called on start command and so what happens here of course is that the oncreate command of the service is called to kind of initialize it and then on start command is called and that passes in the intent along with some other stuff that may have been passed with the service that's that's passed in and that's how you get a chance to find out what the client that started this thing wants to have happen at this particular point so then at that point you can do do whatever you need to do to process stuff in our particular example then I'm skipping over a bunch of things here and I'm not showing you all the details because we're going to cover it later you might have a service that's going to download files and so in that service we're going to have some method called download file or download bitmap or download something or other and it's going to take whatever's passed in which it might very well get from the extra that was passed in and it'll then turn around and download the file now again there's a whole bunch of different variations on a theme here but let's assume for sake of argument that our service is running in a background thread or a background process then that thing can block without affecting the way in which the activity is going to behave because the activity is actually not doing the blocking okay any any questions about any of that something I'll talk about later there's no necessary reason that a service that started either a bound service or a started service will run in a separate thread of control than the caller but it's not uncommon to have that happen in fact it's also not uncommon to have the service run in the separate process and we'll talk more about running things in processes and threads and what the trade-offs are between these as we get a little further along when the operation is done then the service can be stopped and it can do this a couple different ways it can call stop self it can stop itself or it can have some other client stop it it can have another client say stop service which will shut it down so for the one-shot service kinds of things they typically stop themselves when they're done and that causes the service to be destroyed and and the resources are reclaimed okay so that's basically started service there's a bunch of examples of started services we'll talk more later about how you determine whether something so started service or that the long and the short of it is that it's typically called by start service and it has a hook method called on bind which we don't show here because it's not relevant for started services and that typically returns null that's a good indication that something is a started service versus a bad service I'll talk about the bound service later so with the with the started service then some examples would be the the MMS and SMS services that are used to process MMS and SMS messages that go to and from the device when a user makes an SMS request it can start a service to do the actual transmission of that device because it's going to go out over the network overtop of tcp/ip for example likewise when data arrives on the network then that also goes to a service called the transaction service which is a service that runs in the SMS MMS implementation and that gets the message from the network stack and then figures out how to get it to the user typically by using some kind of notification prompt to alert the user they have an SMS message and ringing a bell or beeping or something like that another example of a started service is something that's called the alert service this is defined an Android to handle calendar alerts like it's you know you've got a meeting in 15 minutes and so a little alert pops up and says you have a meeting in 15 minutes don't forget to show up or her class starts or whatever so those are good examples of started services they're kind of one-shot things they run and when they're done they go away and they get reconstituted every time there's more stuff to do so the key theme with the started services things are activated on demand I'll keep that in mind because we'll talk more about that as we get a little further into the patterns that underlie this stuff a couple other things to note so if you are interested in learning more about services go over and take a look at at Android at the implementation of Android and C I'll go show this to you hopefully my network is working there we go so go look at Android 4.1 packages apps so so in packages apps and in a couple other places like packages provider and so on there's a bunch of services that are defined in here and if you if you do a find operation or you search you can find lots of examples of different parts of Android that have services you can see there's a whole pile of them in there and so I recommend if you're curious to see how you implement a service and you're not really sure how go take a look and see what you might find in there you can see that there's also some that are part of the providers directory like the download service for example and media scanner service the MTP service which I think is used for transmitting like image camera pictures and stuff like that and so on and so forth okay so that's just some places to go to look to find examples of services industrial-strength examples of services things that come from Android itself okay so that's that's a started service let's not talk about bound services we're going to come back and talk more about each of these things and I'll show you examples on how to program them and we'll talk about the patterns that underlie them and so on and so forth that's just a quick tour overview so a bound service can be used by an application component to to start the service if it's not already running and if it is running to bind to it so it can carry out a conversation over a connection that remains up and running for some period of time so where a started service is created afresh each time you invoke start service and it's not already running the bound service is typically started and as long as there's someone connected to it it'll stick around it's persistent it's sticky and as a consequence it's more efficient if you're planning to do a long-running set of interactions if you're just planning on sending an SMS message and then not doing something for a long time started service makes more sense because it's not going to keep Android resources tied up while you're not using it so the way that you actually use a bound service is not unlike the started service in some respects you create yourself an intent and you go ahead and figure out who it is you want to talk to what the name is of the particular element that you want to be able to interact with what's the name of the service you want to talk to but rather than calling start service you instead call buying service and as you can see buying service takes the intent but it also takes some other stuff it takes something called a connect and we're going to talk about this a little bit later when we look into more detail about how balance services are actually programmed but for the time being what happens under the hood and when you read the documentation it's a little bit confusing at first there's kind of this dispatching it takes place back and forth it's sort of a handshake that takes place between the client and the server and state is typically set up on both sides in order to be able to optimize later communication and we'll look at all that stuff in in much more gory detail when the time is right you can take a look at this link to learn more information about a balanced service and what it how to program at what it does when you call buying service that results to a couple of calls on the service side the implementation side so of course the oncreate method is called to initialize the service and then there's also a call that's made to something called on vine and on bind is a factory method that is typically used if you're implementing a bound service to return a so called binder I binder reference and this is something that typically resides points to an object that lives in the service context and what it gives back to the caller is a hint is a proxy that is used when the caller of this service wants to send data back and forth and you'll see part of the the dispatching and the handshaking that takes place is to exchange the proxy from the server services side back to the client side so the client can stash it away and then it can make direct method calls on this particular proxy in order to do its thing when we talk about bound services later we'll talk in detail about the proxy pattern which is used to basically provide an interface the client uses to access the implementation of the service irrespective of where that thing resides is it in the same address space is in a different address space that's up to the configuration mechanism that's used you can decide this using your manifest file and it's also something that Android can optimize in a few cases if it can discover something as local it can go ahead and and short-circuit some of the inter process communication so we'll come back and talk about that a little bit later that's not going to be the focus of today's class but we'll talk about that on Monday so as I mentioned there's this really interesting dispatching handshake protocol it's used to go back and forth this is one of those things where it really pays to have an interaction diagram to show the back and forth callbacks because otherwise it's somewhat mystifying who gets called and when they get called and what context they're in and stuff like that so we'll look at that when we get to the right point once you've got a bound service then you can go ahead and invoke operations now the the typical thing to do although by no means the right thing to do or the most appropriate thing to do is to do two-way synchronous invocations between the client that has the proxy it got back from the service implementation so the client can invoke an operation like it might say download image and then on the other hand you've got the service and the object that implements this thing running perhaps in a different context maybe even in a different process and so those are the two parties that are interacting here communicating back and forth by method calls and out-of-the-box unless you do something to the contrary you get so called two-way synchronous communication and what that means is that the caller blocks waiting for the call to return and that call may take place someplace else the way that the communication actually works under the hood and we'll look at this in in quite a bit of detail later is by using something called the binder and the binder framework is a local loopback based intra device communication framework that's used to ship typed messages from point A to point B where point a and point B may reside in different processes they don't have to but they may and it's responsible for doing a bunch of magic to handle all the communication details the memory management the connection management the data transfer and so on and so forth necessary to move data from one address space to another address space I will talk more about that there's a lot of cool stuff that lurks in the context of these proxies and how they work and the way that you program this stuff is by something called the Android interface definition language or a IDL and if you're familiar with Java and Java interfaces a IDL looks almost identical to Java interfaces there are a few differences but it's very very similar and it's actually processed by a pre compiler by a translator that takes the descriptions of the interfaces that are defined at a IDL and it generates automatically generates these things called proxies and stubs and we'll come back and talk about that now I mentioned and I'll just say this in passing now we'll cover it much more detail later out of the box unless you do something to the contrary these communication calls our two-way request response you block you wait for the response to come back it is not hard at all by using some interesting patterns that we'll talk about in order to be able to change from two-way synchronous communication to be able to have asynchronous communication between the caller and the service and the trick is to define essentially one-way operations in a IDL and they don't block and so you'll end up with two one-way operations one to pass a request to the service along with a callback and then the service when it's done processing takes the callback and then invokes a method to get the response back to the client we'll talk a lot about that that's actually my preferred way of using this stuff although you'll have to dig a little bit to find a lot of discussion about this in the Android literature a lot of people don't really think about this too much and as a result you can write software that tends to behave improperly if things take longer to run than you want can anybody think about why you might have some problems if your calls block synchronously between the activity that invokes them and the service that processes them what's what's the whole problem we have in in Android about not having long running operations in the activity it'll block the man sort of control of the wait too long you get the application not responding the dreaded applications not responding or ANR exception thrown and then you'll you'll have a bunch of problems on your hands so for that reason it's often a good idea if you really want to build bulletproof applications to do them as two one-way calls as opposed to one to a call even though it takes a little bit more work to do it makes your program a lot more robust and resilient and so we'll talk about some of the patterns that can be used in Android to do that in fact in some sense it's a little bit like the active object pattern we were talking about before where you have the callback model with active object if you recall active object pattern there's a couple different ways you can use it you can invoke an operation then you can set them you can pull kind of get the result or you can invoke an operation and give it a callback and when the things done it'll call you back and that's kind of the way that the asynchronous model works for for dealing with with a IDL and brokers and stuff like that so we'll come back and talk about that under the hood this is all implemented by something called the binder driver which is a device driver that lives in the Linux kernel and it handles all the low-level communication and if you really want to trip yourself out take a look that code is written in C and C++ it's very low-level and there's actually a few people around here who've who've looked in detail at that code so jules white is kind of an expert on binder driver implementations so if you're ever curious about that you could ask him how it works now unlike the started services where it's kind of a fire-and-forget model you start them up and then when they're done they shut themselves down when they're finished with that one request that they're processing with bound services typically the bound service will run for as long as there's a client that's bound to it and as long as that clients there with a binding then that service will continue to run so that's really meant for long-running conversation type interactions and of course when you're done if you're if you want to get rid of the the service you can call unbind service and if you're the last client you unban the service then it'll go away and it'll destroy itself typical life's life lifecycle kinds of operations done through callback cooks not unlike activities very much the same kind of idea okay any questions about this concept yeah John are their permissions really to the services because I know it's really easy to find yourself - other than when you're like for example stop service you know what anybody necessarily stopped lectures yeah so you can also control those kinds of things in android has pretty sophisticated permission checking system built into its activity manager service that makes sure that you're given authority to talk to various parts of the system absolutely yeah here are some examples of bound services in Android so we have the the Bluetooth headset service which kind of a funny thing but that's used as a bound service media playback service which is used to basically play media you know files audio and stuff like that video in the background which is important because you don't want if you're switching activities but you want to play a song but you want to switch activities you don't want the music to die the second you switch activities and there's also some interesting stuff with the way that exchange email works in Android it kind of runs a service in the background and is used to transmit diffs between to synchronize do data synchronization between what's on your phone and what's on your cloud server running exchange undoubtedly there's also similar kinds of things for Gmail but the source code is not easily understandable gmail as you probably know does not come with source code and even if you are so brazen as to reverse engineer the byte code back into Java you will find that the people who wrote Gmail have obscured the code so they have a little tool that runs dude software before they ship it and it changes all the method names to like you know one two three four and it changes all the variable names so like a ABCD so if you read the code it is absolutely incomprehensible what it's trying to do with with a very few exceptions so that that's because they that's they consider that very important I think they do the same thing with the Maps code as well you can't really see what it does by decompiling okay so to kind of wrap up this discussion applications can use services to implement long-running operations that take place in the background started services as we'll see in the next part of this module are very easy to program from the point of view of just starting them up and passing them some intense and then bound services are a little bit more complicated to program but they also give you some other powerful communication mechanisms they're a little bit more like normal programming invoking operations on objects but where those objects reside can be left to a late binding decision okay any questions about the overview so for your next assignment you'll be doing a variety of things but one of them is you'll be doing the started services into fact to be doing something called an intent service okay so now we're going to talk about is how you would actually implement services and the way you're going to subclass them and some of the lifecycle hook methods and so on and we're going to start by talking about started services and then I think probably Monday we'll continue on talking about bound services and as we go through the discussion we're going to try to emphasize both the commonality and variability that's provided by the different mechanisms in Android it's it's a framework after all so it's got this neat property of commonality and variability and once you understand those properties it makes it a lot easier to figure out what it's doing and it makes a lot easier to figure out how to extend it and customize it for your particular needs so in many ways implementing a service is a lot like implementing an activity you inherit from some base class service or intent service or something and you override certain hook methods that handle lifecycle activities for creating the service or getting intents passed to it or shutting it down and so on and then you have to go ahead and include the service in your manifest file so it knows so that the system knows of its existence and can automatically start it up when when necessary you typically Android typically informs a service that things are happening by invoking callback hook methods on it at the appropriate time and so from a commonality and variability point of view a service gives you a common way of being able to describe activities that run in the back tivities services that run in the background functionality that runs in the background or capabilities are run in the background and that's the common part use your common interface with common hook methods and then it provides you with this set of hooks that you can override to fill in the blanks for your particular kinds of service so let's talk about some of these hook methods you'll see that there's slightly different hook methods for started service than there are for bouncers they both have on create methods they're surprised that's kind of the virtual constructor that's used to initialize the service when it's started however it's started the on start command is called each time a service is sent to command by a start service so that will be called back and that's what's going to give you the intent that was passed this is what a started service does keep in mind the bound services don't look quite the same way and then after you've been stopped after your service isn't stopped either because you stopped it or it's someone else stopped it then the ondestroy hook method gets called to let itself clean up so that's kind of like a virtual destructor that's what's used to clean up the resources now here's something important and this is a little bit confusing at first there's nothing in a service that causes it to automatically run in a thread a separate thread or a separate process if you don't do anything to the contrary you just make a service and you have an activity started it will actually run in the same thread of control as the activity that called it it just will have some restrictions on what it ought to be able to do like it can access user interface mechanisms there's a whole pile of easy ways of getting it to run another context however and we'll talk about a few of them you can spawn a thread and have it run under control of a thread you spawn it's kind of called a free threading model there's also some other mechanisms we'll talk about later about how to get it to run in separate processes or threads okay so let's talk a little bit about how we program this this goes into more detail about what we had talked about before so you start this thing by calling start service typically an activity and keep in mind by the way that things like start service and bind service these are all inherited through something called the context and the context kind of provides this implicit context that's always available in an application that you write and it not surprisingly it has a bunch of threads specific data and it stores things in a per thread manner and so on so what you typically do is you typically create an intent and intent is basically a data structure that keeps track of some state and some flags in a canonicalized way and it basically is used to identify who is going to process this thing and you can either have explicit ways of saying I want this intent handled by this particular service implementation that's explicit mapping of intents to services or whatever or you can let the by the the intense framework ferret it out on your behalf by taking a look at what's in your intent and then seeing what types of services activities broadcast receivers etc what kinds of components have registered to using something called intent filters to receive the information when it occurs you can also like I mentioned before put extras into the intent so it kind of buffle puts these in these things into a message and when you're done you go ahead and call start service the start service call doesn't block so it's going to do the minimal set of things necessary to get that request sent out across to whoever the receiver is and it will return right away and the intent will then be delivered by this call to start service which is defined on the service itself the other thing to remember is that these started services typically just do one thing so here's an example of where we do on start command and something happens started services do not return results to the caller directly they do return a result so on start command returns a result but it's actually returned to the server side or the service side android framework and it gives some information about how to treat the service if if things crash or get stopped or restarted so you can say things like you know redeliver the intent if the service gets shut down and then comes back up again then if you return a certain value that the intent will be redeliver you can also say don't redeliver the intent on to the start command you can say don't restart this service unless the application restarts it so there's a bunch of different ways to to indicate to the android framework how it should treat this service with respect to its lifecycle if it gets shut down unexpectedly and remember in Android you can be shut down unexpectedly for all kinds of reasons usually it's the case especially back in the battle days when there weren't a lot of resources you'd be running low on memory and the low memory killer would come along and say you know that service is running in the background the there's no user directed activity to it let's go ahead and kill it and let's shut it down and so this is used to control what happens when it when there's memory again and it gets started back up or not and you can take a look there's some discussions about how some of the semantics have changed a little bit with service service behavior over time once you've implemented the service and we'll look in more detail how to do this in a second then you have to register it with the intense framework with the Android infrastructure with the activity manager and which handles services as well as activities I don't know why it's called activity manager it should be called the the intense framework service or something like that and basically what you have to do is you have to tell it about the services that you're making it goes in your manifest file so here's an example of some of the snippets of some of the stuff that you'll find an Android sir for example for the MMS service you've got this thing called the transaction service which is a service that's used to send data for when you send an MMS the services you use to actually deliver it over the network over the cellular network to some sell your MMS MMS see I think MMS service center or something like that it used to direct the data and that could block so it runs in a separate context and then there's also an SMS receiver service which is used when SMS messages come into the system that gets called back to deliver the messages to the right place and you have to indicate this in the manifest file using tags some of the kinds of tags you would use for delivering things to activities are describing activities one of the other cool things you can do is with just a little tiny tweak to your manifest file you can actually direct Android to run your service in a but process so what does that mean well normally your service runs in the same process as the color by starting something in a separate process there's a bunch of interesting things that happen does anybody want to hazard a guess as to why you might want to run things in a separate process so if your process gets killed and it might get killed or may crash or may hang or all kinds of bad things can happen this is a little bit less important in Joppa than it is in C and C++ because it's a little harder for services to go berserk in Java and crash other things than it is in C and C++ if you really work at it you can cause trouble in Java but it's a lot harder and so running things and processes for isolation is a little bit less important but it does give you this isolation property and you can also sort of share things and and have them in common and there's a whole bunch of other stuff you can do so I recommend you take a look and read up on starting services with the process directive what I'd like to do now is give you a little bit of an overview of the intent service and one reason to give you this overview is because this is one of the things you have to program in the next program you sign so what the intent service is is it's basically a very common way to program a service and it defines a base class that inherits from service and then you'll come along and subclass from that base class and so typically what happens is when you launch an activity that is what an activity launches a service by starts service and it's an intense service then some magic happens behind the scenes and we're going to talk about that magic you can take a look at this link to find out more than you ever wanted to know about what intent services are intended to do so basically what an intent service does is it handles requests that are intense and it runs them asynchronously in a separate thread of control relative to the caller so the intent service runs in a separate thread and it does some interesting stuff and the way this works and it's actually really take a look at the implementation of intentservice we can kind of poke around with that if you're if you're curious but basically what it does is it automatically starts up a separate thread when the services started and as long as there's work for the intent service to do then there's a worker queue we'll talk more about this in a second and it repeatedly pulls the data off the queue and it goes ahead and calls the on handle intent hook method and that's where you write your code so you subclass this thing and you write the behavior of what on handle intent does and you can be assured that when that thing is running it is running in a different thread of control than whoever called it so I'll talk more about that the pattern that that embodies the the pattern actually patterns that this particular mechanism embodies are the command processor pattern number one which is a postal one pattern pattern elected soft rockatuer volume one pattern and it also embodies the activator pattern which is a pattern that should have appeared in pose a - it appeared in a couple other places you can get it from my website we're in the process of about starting the second edition of the posted to book and I assure you that activator will go into the second edition of posta - so it'll be in there where it belongs and it's basically a pattern for launching services or contexts or processing on demand so those are the two patterns that are implemented by by the intent service framework so when the client calls start service with the intent then that goes ahead and causes the intent service to be created and in the oncreate method of the intent service it goes ahead and does some stuff to get a thread up and running let's take a quick look at that it's kind of fun go take a look and see the implementation if I can find it let's say fine extends service there we go so this is the intense service and as you can see an intense service is a service so it inherits from a tent let me get rid of the funky coloring here so an intense service is a service and it's an abstract service which means you have to come on and fill in something and it's something you have to fill in is this abstract method called on handle intent so that's what you're obligated to fill it now it's got this really interesting pattern that gets used all over the place in android wherever people want to write started services that run in the background in a separate thread and basically the way it works is they define something here called a service Handler and if you if you google if you Google if you if you graph or find or whatever in Android source code for service handler extends handler you'll see this example shows up many different times so what it basically does and this is kind of funky it defines a class that's nested inside of intent service and this guy essentially is going to be passed a looper and we'll see the looper is going to be connected to a separately spawned handler thread and then there's a handle message method remember handle message is what gets called back when you do a send message to something this handle message method is going to turn around and call handle intent on handle intent which is actually inherited by the subclass of intent service it will call this guy back in order to deliver the message in this other thread of control and then it will go ahead and stop itself so it'll go ahead and shut itself down once it's done all right so that's that's kind of how the service handler idiom works and you see this all over the place here is the oncreate method so what oncreate does as you can see it goes ahead and it creates a new handler thread number a handler thread will be running in the background it starts or it creates a thread that'll run in the back Brown and it starts it so this thread is now running and then it goes ahead and it grabs that threads looper and it stuffs it into this thing called M service looper and then it goes ahead and creates a new service handler with the M service looper as the looper that's the parameter passed to it that was the thing that was up here and so what that means is when the looper is running when somebody calls send message and we'll see how that gets done in a second it's going to end up calling back handle message in a separate thread of control but thread the corresponds to the handler thread and that will then turn around and call the on handle intent hook method which will then be dispatched to your user code that you subclass from intent service so here is arm on start when the on start method gets called and and this is a sort of a low-level method gets called by the Android infrastructure it goes ahead and uses the service Handler to get a message now keep in mind this message is going to go to a handler that's being handled by a background thread and then it says hey service handler please handle this message I'm going to send you a message for you to handle so when all on start gets called it is a calling send message and as you can see what happens here is that that will end up calling back to the handle message hook method that's defined on the service handler which is running in a background thread which will then end up dispatching the on handle intent hook method of your class at subclassed from intent service so a lot lots of moving parts here main reason I talked about this is it's used very frequently throughout other parts of Android in the implementation it's kind of cool and we'll see you'll see probably not in a second because I don't think we have time but we will see next class this actually implements the command processor pattern so that's the pattern under the hood that is implementing this if you take a look down here at the on start command method you'll see by by default on start command just calls on start which goes ahead and does that message passing and so it'll also based on a few things that were set when you start it up it'll set what kind of stickiness you want to have in this case which you don't want it to be sticky and you'll also notice that if you inherit from intense service and you for whatever reason want to override the on start command then you need to call super on start command first and then do your other processing that's a very common behavior in Android you call super blah blah and then you do your stuff so that way you can override the behavior but get the the guy above you to do some other work the on bind method is null because this is a started service not a bound service and there's the on handle intent so anyway it's really really really concise and simple but it does some cool stuff on your behalf so let's go back here and take a quick look so as I was saying you know you extend the intent service class you fill in on handle intent method and then that method will get passed back your intent in a separate thread of control and as long as there's work in the work queue this thread will not decide the service intent service will not shut down it's only the queue drops to zero that the intent service shuts itself off so there's a big burst of requests that show up from different applications from different activities you will keep the intent service running until there are no more intense and then it'll go ahead and shut itself down so it's pretty cleverly implemented so here's a very simple example this is kind of like your solution in some sense a little variant of that so and don't implement your solution like this let me repeat that do not implement your solution like this because it's not the same as your solution but it has elements of your solution in it um so we make a threaded download service which it extends intent service and it's on handle intent method whoops which should say intent intent goes ahead and takes a look at various things and based on what it finds it'll go ahead and do some work so we inherit from the service the intent service class and the on handle intent method is basically this lifecycle hook method that is called back by the intent service as we just saw in the code and if you want this thing to run in a separate process you just have to go ahead and add this little little metadata to your manifest file and I'll say run this thing in its own process note the inversion of control you know we talk a lot about frameworks this is another great example of a framework you're not writing the control loop you're not dealing with a low-level message passing you're not dealing with concurrency you're not really dealing with synchronization all you know is the somebody sent you an intent and that intent is being run in a some sort of control and so you're being shielded from a lot of low-level details and Android is calling you back at the appropriate time um let's see if we have a couple of minutes I don't want to yeah we'll go ahead and stop here what I'll talk about when we start next class is I'll talk about how to compare service with intense service and then I'll compare service with thread with async task and then I'll show you a whole pile of examples and we'll talk about a pattern
Info
Channel: Douglas Schmidt
Views: 18,657
Rating: 4.9470201 out of 5
Keywords: Android (Software)
Id: gxj4sQX9m5g
Channel Id: undefined
Length: 47min 30sec (2850 seconds)
Published: Thu Oct 10 2013
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.