Trying out Square's OkHttp client
Trying out Square’s OkHttp client
This is a simple example of implementing Square’s OkHttp library in an Android app. Basically, OkHttp is intending to provide a fast HTTP+SPDY java client.
OkHttp
Step zero is getting OkHttp either as a jar, or pulling down the project and building a jar with maven. When I built this, the jar was not available, so I needed to build it myself. This was quite simple, all you need to do is make sure you have Maven2 installed, and follow the instructions on OkHttp’s github page.
One thing to note is that you need to be building against the parent project, not just the okhttp dir. Sometimes people package up git repos such that there are actually multiple projects in a single repo, and you only need to use one of the dirs in the project. In this case, you need the parent, it will build the child projects for you.
Building:
mvn clean
mvn package -DskipTests
After you build, the jar will be in okhttp/targets.
This git repo bundles a version of okhttp that I build, but it would be better to pull down a more recent version.
Otto
I’m also using Otto here. Check out my post on Otto for a quick primer.
Onto the code!
First up, since we’re using Otto, we register with the bus first. Then, the OkHttp logic is placed in an AsyncTask, so we’ll kick that off here too. This code lives in an Activity’s onCreate.
Here’s the logic for connecting to a site, reading the response into a string, and sending a message out onto the bus with that response string.
This is the method that’s subscribing to the bus, waiting for that response string.
Playing around with Otto on Android
Playing around with Otto on Android
There are a few nice Open Source libraries for Android that Square has published. One of them is Otto, which is a Guava-based event bus system that uses annotations and code generation. Basically, it saves you from needing to create a bunch of interfaces and register them between various parts of your code. Instead, all you need to do is register with the singleton bus, and subscribe to events.
Here’s the sample bus provider that Square published with its sample app:
Next up, register with the bus. This can be done in your Activity’s onCreate, or better register it in onResume, and unregister onPause:
Events can be published on the bus using the ‘post’ method. The object type and the subscribers determine automatically where your event gets routed. Here’s an example showing an event being fired when a button is clicked:
Subscribing to events is very simple. Again, the object being passed is what determines the event routing.
Full code on github.
Verizon Wireless broke my brand new Chromebook Pixel LTE
Verizon Wireless broke my brand new Chromebook Pixel LTE
Wow, looking at my last few blog posts, I’ve had a bad few weeks dealing with corporations. After this, I promise to get back to my regularly scheduled programming and not complain so much. Alright, on to today’s story.
Why I’m writing about this
Chromebook Pixel LTE owners should read this if they’re planning on activating their SIM, especially if they’re adding it to an existing shared data plan, as opposed to simply activating it through the guided tool provided with the device. I don’t know exactly how Verizon broke my device, so I’d love to hear from Google if they have any thoughts on this.
My Pixel
For a few months now, I’ve been really wanting to pick up a new laptop. I had my company’s laptop, and a few devices at home, but nothing that I could really feel free and comfortable hacking on my own projects on. I had been looking around for a while, and sort of settled on a Macbook Retina 15. I liked the specs, and the great screen, but I wasn’t very excited about getting another Apple product. I had also looked at a few PC laptops with the thought of installing Linux on them. However, the best supported among those options was the Dell Sputnik 2, and I was a bit worried it being able to handle a few use cases. I also was a bit worried that if I bought a machine to install Linux on, that I would spend more time playing with Linux than I would developing. Then, Google announced the Pixel, and a few Googlers were posting about crouton. Crouton is a project that allows Chromebooks to run Linux in a chrooted environment, with full hardware support for just about everything that you could think of, including being able to use multiple displays. Perfect.
I decided that a home server would be a good compliment to the Chromebook, for doing the heavier sorts of tasks that I like to run once in a while, like compiling Android from source. And, buying the Pixel and server together was less than the Macbook Retina. I decided to go with the LTE version since I have Verizon, and occasionally will tether my phone to my laptop when I need the web, and I figured that I’d prefer to have something on-board rather than killing my phone’s battery.
Setting up the Pixel
Now, as I mentioned, I wanted to be able to run crouton, so that meant that I needed to enable dev mode on my Chromebook. Enabling dev mode means that you basically wipe the device, and start from scratch, running an unverified instance of Chrome OS. From there, you can set up crouton and install Ubuntu. Now, anyone who’s installed some flavor of Linux on a laptop knows that no matter how well supported the device is, there are still going to be pain points, things that will require you to spend some time and solve. The Chromebook Pixel was no different. That’s not to say that there were any overly complicated stumbling blocks, but there was a decent amount of setup, couple with my setting up things like Eclipse and ADT for my Android development work. Altogether, I’d estimate that I had put about 15-20 hours worth of work into getting my environment set up the way that I wanted, and eliminating the issues that I had initially had with the setup.
Once I had the thing set up, I was very happy with it. The Pixel checked all the boxes of what I needed in a machine, and an environment. The next thing to do was to get the LTE set up, so that when I go off to coffee shops with over-crowded WiFi, that I could still be productive. Off to Verizon!
EDIT: Instructions on how to do this yourself.
Meanwhile, at Verizon Wireless
I made the trip to a local Verizon Wireless store to have my brand new (< 1 week) Chromebook Pixel LTE device added to my shared data plan. My wife and I have a shared data plan, and adding the Pixel was supposed to cost around an extra $10/month, I figured that’s not a bad deal. We go in, and the reps are pretty nice, the guy that I was working with hadn’t seen the Pixel before, but seemed to be familiar enough with Chromebooks, at least in theory. We got started, and he asked me to hand over the device. No problem, I figured that they were used to doing this sort of thing, what could go wrong, except for maybe losing my browser session.
When he handed it back to me the first time, because he couldn’t find the SIM card’s IMEI, I noticed that he had killed my browser session. It was annoying, and certainly inconsiderate, but not a huge deal, I was looking up some stuff on Go Lang, nothing I couldn’t find again. I didn’t think much of it. I found the IMEI, and handed the device back. He seemed to be having trouble with their system, in trying to add the device to my shared data plan. This was a bit annoying, but it’s a brand new device and apparently Verizon’s process is device-centric. With Verizon, they don’t have a general process where they can simply take a SIM card, say, this now belongs to so-and-so’s shared plan, and will cost $10/mo to connect. This seems like the way it should be, but it isn’t. Instead, they have to find the device in their system, and then see what plans are available for it, and then see if they can hook it up to an existing account. Apparently, the tablet version of their software was allowing them to do this, but the desktop version wasn’t. No idea why, I didn’t really care either. At this point, the guy called over a manager to help him out. She knew that there had been a rep that had done this before, but apparently nobody in the store had, or knew exactly what to do, so they were going to just muddle through.
Eventually, they were able to get the plan added to the account correctly, and all that was left was to active the SIM. They asked me to reboot the device, hoping that would help. I rebooted it, signed in, and still was unable to connect. I handed it back, and they worked on it for another 5-10 minutes. Then, they seemed to get excited, saying that they had successfully activated it, and that I just had to log back into my account. This time though, when they handed me my device the ‘login screen’ was not the login screen, instead it was the device setup screen. WTF? I was very confused.
I entered my credentials and was greeted with a blank, fresh screen, just like the one that I saw when I booted the device for the first time. I was very worried at this point. I tried opening a shell, a sure-fire way to test if you’re in dev mode or not, I opened the console and entered 'shell’, it returned “Unknown command: 'shell’”. Shit. I rebooted the device, no dev-mode scary warning screen. There goes 15 hours worth of work.
I am livid.
I calmly looked at the manager and informed her that they had wiped my device in the process of setting up LTE access. She didn’t really know what I meant, and I tried my best to explain. I said that everything was gone, not just my account, but everything on the device, things that weren’t a part of what gets automatically backed up. She was very apologetic, and I let her know that a simple apology was not going to cut it. She asked me what I wanted her to do, and I said, make me an offer. She went into the back room for about 10 minutes or so.
When she came back, she said that she had spoken with their financial department and determined that they would give me a $35 credit to my account. I believe that that’s what they charge for device activations. I calmly explained that I had spent about 15-20 hours configuring the device, and that I would have to do that again. I also explained that if I were to bill out my time hourly, the low end would be at around $100/hr. I said that a $35 credit was not going to cut it. I tried again to get her to understand what she had done. I said, “imagine that you had given me your laptop for me to install something on it. I do that, and I hand it back to you and everything is gone. All your music, all your data, everything. How would you feel? Do you think $35 would cover it?” Unfortunately, my time had run out, and I needed to leave. I couldn’t wait around for another round of her checking with the financial department. I asked her to have them call me tomorrow.
Why I’m so upset
One thing that really bugged me about the experience was that neither rep took any responsibility for what they had done. They kept saying, “all we did was activate the LTE modem, I don’t know how this could happen”. If you’re going to work on someone’s device, and you break it, you need to accept responsibility for that. End of story. Another thing that bugs me about this is that while it is part of the Verizon rep’s job to activate Chromebook devices, they don’t seem to have had any training about it, or even to know the basics of how to navigate the OS. This is a failing on both Verizon and Google. Google went out with an LTE device, with Verizon as a promotional partner, and didn’t make sure that the Verizon reps had the proper training to deal with the device without breaking it.
To be fair to the reps, what likely happened is that they rebooted my device, and hit the space bar - that’s how you get the device back into verified mode. I had asked them if they rebooted it, and they said that they hadn’t; I honestly don’t know if they knew enough about what they were doing to be sure. It’s also possible that activating the new SIM card really did hard-reset the device, or that part of their instructions were to take it out of dev mode, and they simply didn’t own up to that. I don’t know exactly what happened, because I couldn’t see what they were doing. Regardless, what matters is the result, and that they caused it. I trusted them with my device, and they violated that trust.
Google is owed some of the responsibility here for making it so easy to wipe out a device in the course of doing something seemingly simple, like activating a SIM card. I’ll be filing a bug report today on Chrome OS about switching between dev and verified modes, that it should require the primary user’s password.
Where things are now
There’s no resolution at present. I’m waiting to hear from Verizon. I would like them to offer me something substantial for the grief that they’ve caused. I will also be asking them what they plan on doing in the future to ensure that this sort of thing does not happen again. I will update this post when this issue gets resolved.
Updates
Update 1:
+Charles Hardy mentioned that if you can talk the VZW reps into giving you the card and doing it yourself, it’s a fairly easy process. He said that you just need to get a SIM that’s been added to your account, and replace the SIM in the Pixel with the new one. Then, reboot and go through the activation process on the Pixel like normal.
Update 2:
Just got off the phone with Verizon, they offered a $55 credit, $20 more than the last offer. I told them that that was unacceptable, but the manager I spoke with was not willing to budge. We’ll see what happens next.
Update 3:
Submitted as an issue to Google. I went through the process suggested by Google for submitting feature feedback and suggestions.
chrome://help/ -> "Report an Issue"
Update 4:
+Melissa Daniels responded to my G+ post on this, and said that she passed my feedback regarding switching between verified and dev mode to the appropriate team. That’s good to hear!
More bad news on the Verizon side, I logged into my account this morning and found that they were charging me twice as much as they said they were going to when I was in the store. They told me $10/mo, and I’m looking at my account that says $20/mo. The rep that I’m talking to seems nice, hopefully she can get some of this fixed.
Update 5:
Verizon offered me a $120 credit, and I’m taking that one. Amy the CSR came through!
As far as the monthly access fee goes, $20/mo is what Verizon charges for USB modems and netbooks, and $10/mo is what they charge for tablets. They are counting this as a USB modem or netbook, and won’t budge on it. Apparently that’s how it’s in their system, and the various blogs that reported otherwise, along with the in-store rep that I spoke with, were incorrect.
I think that I’ll probably keep the data, since I’ll be saving roughly that amount on reducing my Dropbox usage, though I’m quite unhappy with Verizon on this. There are several reasons that I’m still annoyed, but the main one is that I don’t really understand why they have vastly different rates to connect devices to the shared data plan that you’re already paying for. Some devices are $5, and some are $20.
I think that this is where I will leave off with this post, since the main issue was resolved, and I don’t see any movement on the monthly fee issue.
Update 6:
Really, this is the last one. Melissa Daniels is going to follow up with VZW on this issue for me, which I really appreciate. She’s really working to make sure that everyone with a Chromebook has a great experience.
The last rep that I spoke with at Verizon said that he would be following up with the local store to make sure that the reps there get up to speed on their training, as well as learn how to communicate things like monthly charges better to customers.
All-round, this was basically the result that I was looking for.
Update 7:
Here are instructions on how to do this yourself.
Update 8:
From Melissa Daniels in this post:
Hi all, As a heads up, for those of you who are looking to activate, the steps for activation are as follows
For calling or in store: Process is as follows, user needs their ICCID (sim card ID), IMEI (device ID) and their existing Verizon account # and login details.
Call VZW post paid service at 1-800-256-4646 and press #2We’re actively working to resolve these issues and streamline this process (as well as update our content on our own help center as well as on VZW’s) and truly appreciate everyone’s patience.
As +Trond Wuellner mentioned, the pricing should only be $10 – not $20.
Thanks!
So, that’s $10/month to add the Chromebook Pixel LTE to a shared data plan coming from two Google reps (Trond Wuellner is the other, see the thread). Trond mentioned in another comment that they (at Google) were working with a team at Verizon to get this issue taken care of and fix the pricing for everybody. I will update here again once I see this reflected in my bill, or if there are any other developments.
Update 9:
I did need to call Verizon to get the bill fixed. However, I was only on the phone for about 10 minutes, and everything’s in order, including a refund for the extra charges.
Kaiser Permanente's billing system is insane.
Kaiser Permanente’s billing system is insane.
I work for a very small startup.
We are small enough that buying a company insurance plan doesn’t really get you anything over individual rates. A couple of us are also on spouses’ company insurance plans, only leaving two or three of us actually going through our company for insurance. As a result, our structure is that we choose the insurance that we want, pay for it out of pocket, and then submit the monthly bills for reimbursement. This works out reasonably well, I get the insurance I want, and the company pays for it. Great!
When going through all of our options, my wife and I landed on Kaiser Permanente. The price seemed reasonable, they had pretty good ratings, and the coverage seemed to be decent as well. Initially, things went smoothly. Then, all of a sudden, the bills stopped coming. We had signed up for Kaiser’s automatic EFT program so that we could automate the process of paying them every month, just like we do for every other bill that we pay. I have set up automatic payments for nearly every service that I have used since I started paying bills, as those systems became available.
Manual bill paying punishes customers
The whole process stresses me out. Let’s step through the process for paper bills, you have to watch your physical mailbox and sift through all the junk looking for something important. Then, you get it, and have to open the several important looking things to further weed out junk. You are rewarded by finding something that tells you that you owe money somewhere. Next, you have to write a check, put it in the envelope (usually requiring a stamp, cheap bastards) and mail out the bill and the check, hopefully in enough time to get there by the due date. The whole process punishes you, there is no single reward in any of those steps of bill paying. You need to sift through your mail and are punished for finding what you’re looking for (the bill). Then, you act on that and are punished again - both needing to shell out money, a stamp and needing to get the thing to a mailbox.
The process for manual online payments is slightly better, but not by much. First, you need to keep an eye on your email inbox, looking for sifting through all the junk, looking for something important. When you find a bill, you’re still punished by finding it, in that you’re told that you owe money to someone. Now, you need to go to the website and remember a password, where the password requirements strip out the special characters and shorten the usual password that you use. Now, you’ve managed to log in, and now need to navigate their crappy interface to figure out where you can actually pay your bill. You do that, then you need to pull out your credit card. Now, you step through the overly long payment process and save a pdf of the confirmation page.
Neither of those options are fun, and both of them punish you throughout the process. Many of the services that we use seem to just be there, in the background, and you don’t think about them all that much. I want them to be billed in a way that I don’t need to think about them all that much. I budget for what gets paid, set up the automated payments, and let it run itself. Periodically, I’ll run through and audit things, looking at my bank statements for amounts that differ from what I had expected to see, and then log into those billing sites to track down the bill in question and look it over. This system works out pretty well, and while there have been a couple of times where I’ve overpaid for a few months, I’ve always been able to have it corrected after looking things over and contacting the company involved. No problem.
Kaiser and the EFT
Then came Kaiser. We signed up for their EFT system that was pitched to us along with one of our bills. Great, we thought, no more sending checks in the mail, this will all be handled for us. We signed up, and it was handled for us. Until, a couple months later when the bills stopped coming in. We called Kaiser and asked them to send the statements, and they did. Ok, small glitch, no big deal. The next month, the same thing happened. Again, we called, this time, asking if there was something strange going on. On the phone, I was told that when you sign up for EFT, you stop receiving bills in the mail. Alright, I thought, I’ll just get them online. I checked the billing section of my account and there had been nothing saved in there since we signed up for the EFT. At this point, I had no way to prove, beyond the withdrawals from my bank account, that I was paying Kaiser, or what I was paying them for!
At this point, I was quite confused. Why was there no digital record of all of my bills? The first bill was there, but none of the others. I don’t think that I have ever encountered something like this before.
Kaiser’s response
I asked Kaiser what was going on. They told me that in the EFT agreement that I had signed, it said that we would stop receiving bills. I asked what about the electronic copies, they said that we would stop receiving those too. (I’m going to continue this based on the assumption that they were correct in that the EFT agreement stated that bills would stop coming, however that isn’t true.) I asked how I could obtain a record of payment for my healthcare, they said, ‘look at your bank statement’. I was floored. I asked to speak with a manager.
I spent an hour on the phone with a manager 'discussing’ this issue. I’m fairly stubborn, and logical, and simply couldn’t accept his answer. The answer to this, was repeatedly that when you sign up for EFT with Kaiser, they stop sending you any form of a bill or statement, and that this is reasonable because you should expect it and can look at your bank statement. This didn’t work for me for two main reasons, I need the statements to get reimbursed, and I generally want to have some record from the people that I am paying of what I’m paying for. Another reason that this didn’t work for me was that it was completely illogical. No other company that I have dealt with has ever operated this way. Ok, if I sign up for automated monthly payments, and you don’t want to pay for paper bills to be sent every month, that’s fine, as long as I can access them online.
They claimed that this system was paperless, but it was really statementless! I couldn’t log in to get those statements online, because the statements didn’t exist - or so they claimed. I kept grilling the guy on how they were billing me if they weren’t able to generate a statement, and he kept saying that it was all just automatic, and that this is what I had agreed to (again, according to the agreement, this is not what I had agreed to). He went on to claim that all the companies that he dealt with operated in this way. I said 'bullshit’! This manager was lying to me on the phone. I’ve never heard of a company operating this way, even cable and telecom companies do a better job with billing than this. My main question was this, 'why can’t you generate the electronic bills and make them available to me through your web portal?’ This wouldn’t require much investment beyond ~1MB per month per customer, something they do for anyone who doesn’t enable EFT. It would take years for a single customer to cost them a cent in server storage. He kept claiming that the EFT system just wouldn’t do that, and that I was unreasonable for asking for it. I suppose that the insane part of this is that I kept asking the rep the same questions, expecting different answers. All I wanted to hear was, 'yeah, you know, you’re right, this doesn’t make a whole lot of sense, our system is not set up in a great way, and we should fix this.’ Or, at the very least, 'yes, the system is screwed up, I’ll pass this along to my bosses.’ Instead, this guy claimed that they were doing the reasonable thing.
Ok, let’s do a little math here. To simplify, let’s assume that the storage cost for storing a customer’s records is $0.01/yr. If someone needs to call customer service to request a bill while on EFT, they would spend maybe 10 minutes on the phone. If the rep is getting paid $15/h, then each call costs them about $2.50. For each call that they eliminate, they could store statements for 250 customers for one year. Now, I’m going to use Wikipedia’s numbers for the Northern California region, which has 3,351,449 members. If they stored all the records for everyone, that comes out to $33,514.49/yr. If more than 13,405 people (~0.4% of their customers) call in once in a year or over 1,117 people (~0.033% of their custmers) call every month requesting their bill, Kaiser is losing money.
Kaiser’s business is billing
This was obviously incredibly frustrating to someone who has worked on medical billing systems, and knows for a fact that, even if they are odd and difficult to work with, they can be tied together when necessary. My larger concern was that Kaiser’s business, for the most part, is billing. Billing should be Kaiser’s core competency, their business is to shuffle money around and to keep track of it. Mostly, this means billing customers, sometimes it means paying bills sent by medical institutions. If Kaiser has this much trouble sending me my monthly bill, what’s going to happen when I actually need to use them for something, or when my bill becomes more complicated than my monthly premium?
Conclusion
Again, working at a startup, I simply don’t have much time to dump into investigating this further, or finding different insurance and switching over. I’m strongly considering it. In the meantime, I cancelled our automatic EFT, and the bills have magically started coming again. What do you think? Is any of this reasonable on Kaiser’s part? Or are they just terrible at what they do? Here’s a pdf of the EFT agreement that I found, nowhere in it does it mention anything about paperless or statementless billing.
Open letter to CitiBank on their horrible surveys
Open letter to CitiBank on their horrible surveys
I recently activated a new Citi Card, and had a pretty decent experience with the customer service there. I thought they did a really good job, mainly because they didn’t ask me to repeat anything and two seconds after I said that I needed the card activated it was done, and I was able to get off the phone and move on with my live. Today, they sent me a survey about the experience, and I decided to fill it out, since I thought that the rep did an exceptional job.
However, the survey software that they use seems to be designed to be frustrating and take way more time and thought than should be necessary. Further, I would be willing to bet money that this design is leading to a higher percentage of people like me, who get frustrated and give up a quarter of the way through.
The following is a response to the second ‘comment’ section of a survey that they sent me.
What is the primary reason for the score of 9 you just gave? Please be as specific as possible.
(Do not include any confidential information in your comments such as account number, PIN, password, etc.)
This answer is not related to the question asked.
The design of this survey is so poorly designed that this is as far as I’m willing to go. For one thing, you’re asking me redundant information right now. How is this significantly different from whether or not I would recommend the service based on the customer service experience? Are you trying to waste my time by repeating questions to me, and asking me to write comments to you about them individually?
Do you usually count from 1 to 10 backwards? Why don’t you give any visual queues besides text for the ratings? Are you not concerned about people getting confused and responding the opposite of what they intend to?
Why are you taking up the entire horizontal space of my screen? I have a fairly large screen and actually need to turn my head to see all of this information.
Why am I only 28% of the way through? Do you seriously expect people to click through all the way to 100%? What’s your completion rate for these things? If I were doing this, I would have maybe four pages, and the progress bar would not be a depressing grey with a percentage in it. (By the way, I did the math, and you went from 24% - 25% from the last page to this, which means 4% per step, which comes out to 25 questions that I need to answer!)
Don’t you guys make enough money to be able to afford to build better experiences for your customers? Are you concerned that a terrible experience with your survey software will have a negative impact on the answers given, or reflect poorly on your company?
If your company’s survey looks like this, you’re doing it wrong.
Facebook updates as malware
Facebook updates as malware
Recently, on my Android tablet, I started noticing these odd notifications about Facebook having downloaded an update, where it wanted me to click the notification to install it. This is a very odd paradigm on Android, and I was immediately concerned that it might be an attempt by a drive-by download to get malware installed onto my device. Maybe this is a good point to take a step back and explain a few things.
Android basics
Most Android devices ship with some sort of market pre-installed. Whether it’s the Play Store, or Amazon, this is the main place that most users find, download and install their apps. Generally, developers will publish their apps through these channels. One thing that these markets provide is a basic level of security against certain types of malware, and updates to apps that you already have installed, get handled in such a way that it would be almost difficult for you to go download a malware app pretending to be an update to an app that you have installed. There is usually a ‘my apps’ section in the market where you go download your updates, or where updates are autmatically managed for you. If an app wants to notify you of an update, they should pop a notification to take you to the Play Store, or the Amazon market, or perhaps Samsung’s app market depending on your configuration.
Multiple markets
Determining whether or not a specific market is present on a devices is actually trivially easy, and it should be just as easy to make reasonable guesses on how to fail back to less obvious markets if you find that the more popular ones are not installed.
Facebook’s strategy
Facebook’s new strategy seems to be that they should simply eschew the markets altogether and manage downloads themselves. I’ll take a stab at why they’re doing this, and why they might think it reasonable. Facebook, on the web, is famous for rolling out small experiments and A/B testing live on their site to see if a feature works, or how people will use it. This is really easy to do on the web. On mobile devices, you need to rely on your users updating their app regularly, and if you’re pushing out releases on a daily basis, it’s likely that your users will miss updates, and I would even venture to guess that a lot of users are just not real great about updating their apps on a regular basis. So, what’s happening on the Android app is that they have created their own pipeline for installations.
They notify you directly when there’s a new version, then when you click on the notification, you get a screen that asks you to download and install the update, or that they’ve already downloaded the app in the background, and it’s ready to install. They warn you that the version you are using has been depricated and are strongly pushing you to update. If you choose to update, you’ll be taken through the non-market package installation, which means that you have to have that setting enabled.
Android and malware
Something that many Android users may not be aware of is that malware is starting to become a real thing on Android. One vector of attack is something called the drive-by download. How it works is you visit a website that has been compramised, and you get an apk automatically downloaded to your device. The apk is named something like 'SecurityUpdate.apk’ or something that seems like you should install it. So, some users invariably do install it. It doesn’t seem like a huge problem right now, but it is a real thing, and companies like Lookout have been finding these attacks out in the wild. If you’re in the mood to do some research, I’d suggest Googling around for talks given by their engineers on Android security.
Why this is a dangerous stratgey
The basic problem with Facebook’s strategy is that it leverages the same drive-by download methods that malware does. What’s worse, is that these are real updates, users will start to get comfortable seeing updates being done like this, and as such, will be much more vulnerable to malware attacks going forward. Worse still, it would be trivially easy to copy Facebook’s design of their download/update page, and make it look like you’re going to download and install a Facebook update, when in reality, you’re actually downlaoding and installing malware.
Description of the attack
A Facebook specific attack would be fairly easy to do. First, create a web page that looks like the Facebook for Android update screen. Also, create a malware android app whose name is facebook_update.apk and the app icon is Facebook’s app icon. Then, do a drive-by download of that web page along with the malware app ( source ), and name it something like 'Click_to_download_Facebook_update.html’. This will show up in the user’s notification drawer as the title of the downloaded file, and some number of users will open it. Now, the user is presented with a familiar looking screen, where they can just click the install button like usual, and install the app. Now, just sit back and wait for the installs.
What to do
I am going to advise everyone I know to ignore those updates, and never install through that mechanism. If Facebook keeps pushing it, I’ll advocate for uninstalling the mobile app, and using the web version instead. I’ll also be sending an email to Facebook about this, and asking others to do the same. If you know an engineer at Facebook, even better. This is just completely irresponsible behavior on Facebook’s part, and they need to correct this.
PS - I wrote this, and the sample app from the car (driving from SF Bay to Reno for some weekend skiing), so please forgive any spelling or syntax errors.
Gists in Tumblr
Gists in Tumblr
Displaying github gists in tumblr is not as difficult as I have seen it written. All you need to do is copy the regular embed code into your post. A couple of caveats, first, it won’t show up in the preview. Second, it seems to work best if you’re in markdown mode, instead of text or html. I have a post which uses multiple gists in a single post, so that works fine too.
Example:
Image scraper test
Image scraper test
The following blog post was written over a year ago. The app discussed, Pin’d, has since been completed, published, and removed from the Google Play Store. I have decided not to modify the post, because it still contains lots of useful information. I also open sourced this image scraper since the original post.
I’m excited, I just got my image scrapper up and running for my Pinterest Android app, Pin’d. I wrote it as a separate project, and the coding was a couple fast hours yesterday at the coffee shop, and then an hour debugging this morning. It works well enough to dump it into my Pin’d project, and then I will simply chop it up and make it a bit more robust and stable. Currently, it only builds images based off of a full path, and also only for images that are within an img tag. I will probably keep the tag requirement, but I might be able to do something about using relative paths (really, it’s written in, I just need to test it). Oh, and if you’re really confused about what I’m talking about because I started this blog post mid-way through my stream of consciousness, I should probably give a bit more context. Basically, the experience for sharing content from the web in my Pin’d app will be the default ‘Share’ action from your normal web browser. Go to a web page you want to share, click Menu -> Share and select Pin’d from the list. Depending on what Pinterest’s API offers, I might do the same for allowing uploads from the Gallery or simply snapping a photo with the camera directly (this, too is already written). Anyways, once you click select Pin’d as your share action, it will take you to my app which will scrape the images off of the website and allow you to select one that you’d like to share. Select the image and it will build the request and send the information to Pinterest. See below the fold for a couple of images.
Creating Tabs in the ActionBar in Android
Creating Tabs in the ActionBar in Android
The following blog post was written over a year ago. The app discussed, Pin’d, has since been completed, published, and removed from the Google Play Store. I have decided not to modify the post, because it still contains lots of useful information.
In working on my Pinterest app, Pin’d, I decided to switch from a list navigation to using tabs. I also wanted the tabs to hang off of the ActionBar, instead of needing to manage them separately, as this would be the least amount of refactoring, and would fit in nicely with the rest of my app. I also ran into a question on the android-developers google group about how to do this. I figured that these two things were reason enough to code up a sample implementation.
The first thing that needs to be done is to set up a project with either ActionBarCompat or ActionBarSherlock. After using both in different projects, I’ve settled on ActionBarSherlock, and that’s what this post will be referencing. To get ActionBarSherlock into your project, you should download the library and follow the instructions there. If you’re feeling really lazy, I’ll give you the short version. Download the zip and extract it. Create a new android project in Eclipse, don’t automatically create an Activity. Once the project exists, right click it, go to Properties -> Android, check the ‘Is Library’ checkbox and hit 'ok’. Now, right click the project again, select Import -> General -> File System, then select the library directory of the ActionBarSherlock contents you downloaded and import it. Now you can create your new project, calling it whatever you want and letting Eclipse create the default activity for you (if you want). You should have your project in the workspace now, if so, right click it and select Properties -> Android then in the library section, click 'Add’ and add the ActionBarSherlock library. Before you close that dialog, change the SDK build version to API level 13. Now you’re ready to start coding. First step is to add the appropriate bits into your AndroidManifest.xml file. While ActionBarSherlock will build on targets down to API level 7, the target needs to be set at 13. This is because ABS will try to use the native methods wherever possible, and to do that, they need to be accessible to the app. Open up the manifest, and add the following line:
ActionBarSherlock requires that a theme be specified in the manifest. This is how the system knows where to apply the ActionBar and what it should look like. Add the following to either the top application or top activity:
Adding this to the application applies it to all Activities, and applying it to the Activity limits the use of ABS to that one Activity. That’s all we need to do for the manifest, so go ahead and save it and close it. Next, open up the activity that you created. Mine is called 'SimpleActionBarTabsActivity, and is located here:
When using ActionBarSherlock, the Activity needs to extend FragmentActivity instead of just an Activity. The bonus here is that this opens up fragment support for your app to phones running Android 2.1. Fragments are really useful, and you should consider using them, or at least playing around with them a bit so that you know what they are and how they work. You should have something like this:
We can actually do most of the work for this in the 'onCreate’ method, here’s what you need to get two tabs listed:
Stepping through the above code, the first few lines are typical of just about any app. Take a look at the line that says getSupportActionBar()…, this is where we are telling the system that we want to use tabs as the default navigation mode. There are a few different navigation modes to choose from, standard, tabs and lists. Standard doesn’t give you anything special and list mode will give you a drop-down list in your ActionBar. In the next line, we create a new ActionBar.Tab object, then we set the title of the tab, pretty simple. Then at the bottom, we add the tab to the ActionBar. If you do all this, and run it, you should now see tabs showing up within or below your ActionBar. Try clicking them. They don’t do anything, do they? To add the ability to click on the tabs, you will need to modify the class declaration to add 'ActionBar.TabListener’:
ActionBar.TabListener is just like other listeners, but focuses on which tab was selected instead of if a button was clicked or something. The following two lines will need to be added to the 'onCreate’ method:
And the following three methods will need to be added to the class:
That is just about it. I’m sure that if you play around with this, or just by reading it, you might gather that this code doesn’t actually do a whole lot. Currently, selecting a tab just leaves the same content on the screen. But, that is simple enough to fix, just use the three TabListener methods to manage Fragments. Start by adding a fragment, then swap it out using the fragment replace method, or add to and pop off the stack. Although, that is outside of the scope of this tutorial. Feel free to pull down the full github project and play around with it yourself.