Discussion Forums  >  Plugins, Customizing, Source Code

Replies: 11    Views: 86

epicweb
Aspiring developer
Profile
Posts: 159
Reg: Aug 30, 2012
Glen Carbon
4,990
03/05/14 07:16 AM (10 years ago)

Screen Data URL Cache - how does it work??

I'm using wordpress to pull json data for menu screens and maps. I'm trying to understand a bit more how caching works and how it would work if the device does not connect to the internet to pull data. Scenario: Just installed app and the home screen is a menu that has a data url pulled from a php script. - How would I preload the data before I submit the app and then refresh that data if the device has internet connectivity on launch? - What happens if the app was just install and home screen is data url but the device doesn't have connectivity? It looks like to me I get a popup that says "There was a problem downloading some data. Check your internet connection then try again". - Could I copy my json data from php and add it to the config file in xcode before I submit? Not sure if you can do this because the screen using a data url. And if I did this option how would I force the app to pull from the data url if the device has internet connectivity? Thank you for your help!!
 
Niraj
buzztouch Evangelist
Profile
Posts: 2943
Reg: Jul 11, 2012
Cerritos
37,930
like
03/05/14 07:38 AM (10 years ago)
You have a good objective! That would be a nice improvement to an already great caching implementation. For my custom plugin, I had to dig into some of that area to implement a localFileName capability. In my case, I did not want to fetch the data files via the Internet. Instead, I needed to host the 48 data files directly within the Xcode project bundle. Turns out that BT has utility methods "doesFileExistInBundle" and "doesFileExistInCache". Bundling and Bundle is Apple terminology for "the file was compiled for inclusion into the Xcode project". Now you know how to check if the data is inside a file on the device. Next you need to check if the device is connected to the Internet. I am not near a computer, look in the BT code for "reachability" or "connected to Internet". For the particular plugin, you can modify the loadData method to check for Internet connectivity to switch from using the local data to using the dataURL. I am going off memory, don't quote me on the exact names of the methods. You can also look for "parseData" or "parse", the "loadData" will be nearby.
 
David @ buzztouch
buzztouch Evangelist
Profile
Posts: 6866
Reg: Jan 01, 2010
Monterey, CA
78,840
like
03/05/14 10:13 PM (10 years ago)
These are fantastic questions and do introduce some complexities and scenarious that the typical BT projects is both "good" and "not so good" at dealing with. @Niraj points out some good stuff, such as some built-in methods you can use to determine where files are, where they are not, etc, etc. Side note: To determine if the device is online, at anytime, you can use this (anywhere in your project). a) Get a reference to your app's delegate: APPNAME_appDelegate *appDelegate = (APPNAME_appDelegate *)[[UIApplication sharedApplication] delegate]; b) Inspect the app delegates "rootApp" property to determine if the app is connected. if([appDelegate.rootApp isOnline]){ //the device is connected, download the JSON and save it for offline use... }else{ //use a JSON file included in the bundle... } The "rootApp" property is an instance of the BT_device class. Have a look at that class (it's in the BT_Core folder) for a list of other properties you can inspect. ie; rootDevice.deviceModel, rootDevice.deviceVersion, rootDevice.deviceLatitude, rootDevice.deviceLongitude, etc. The best solution will be a to use a combination of this information to get your plugin to do what you want. for menus and maps, where you're pulling JSON if available, you could either modify the existing plugin files or copy them and make your own plugin based on these. Either way's fine. If you copy them you'll need to have a deeper understanding of how a plugin is constructed. Class names, dependent files, etc. I would: a) Plop a JSON file in the bundle for my "map" and my "menu" like mapLocations.txt and menuItems.txt. These would be JSON structured files to be used on the FIRST LAUNCH only - if the device is offline. All cases after that will either use the data at the dataURL (the JSON from your wordPress install) OR a cachedVersion. Cached because you'll be saving the wordPress JSON after you download it so it will always be available after the first download. Scenario 1: App first launch. Not online. Use the JSON in the bundle. Scenario 2: App first launch, is online, fetch JSON from the dataURL and save it to the cache. Scenario 3: cachedVersion exists, device offline. You already fetched it. Use this cachedVersion. Scenario 4: cachedVersion exists, device is online. Either download again (force refresh) or check for newer version then download only if needed. The "if" statement and logic you use will need to account for all these scenarios. It's not too tough to dig through some of the loadData methods I've written that account for some of these scenarios. Gotta love open source, let the hacking begin :-)
 
epicweb
Aspiring developer
Profile
Posts: 159
Reg: Aug 30, 2012
Glen Carbon
4,990
like
03/05/14 10:49 PM (10 years ago)
Thank you very much for taking the time to reply to my questions with so much thought and details. I definitely have a lot of consider and research. Thanks again for working on that example today and your response above. Sean
 
Niraj
buzztouch Evangelist
Profile
Posts: 2943
Reg: Jul 11, 2012
Cerritos
37,930
like
03/05/14 11:55 PM (10 years ago)
Sean -- if you want to work on this together, let me know. I see it as a necessary feature for The Big Game app that Ed and I are developing. Dang, another feature to add onto it -- we will indeed release that puppy from feature creep jail! :-) In fact, it is essential for all the plugins. Once we nail down the code, the Plugin Devs can apply it and update their plugins onto the Market. David is right -- Open Source does indeed rock. The search box and the right-click "Jump to Definition" has led me to many discoveries of all the cool utilities within the BT Core! Hit me up on FB to yap about it. -- Niraj
 
David @ buzztouch
buzztouch Evangelist
Profile
Posts: 6866
Reg: Jan 01, 2010
Monterey, CA
78,840
like
03/06/14 12:43 AM (10 years ago)
ONE more thing, and a learning chance??? This may be MUCH MUCH easier if you use a sqllite.db in your project. The thinking... a) Add a sql database (super easy, google it), one table, "files" or whatever. File content (a BLOB column) and a modified date. b) Load the .txt file from the bundle into the database when the app launches. c) Check for updates however you want. When you fetch a new version of the file, add it to the database. d) Your plugin loads the file from the database everytime, not the file system. Seems like a much cleaner, reliable, simple approach? just sayin' d.
 
shenry
Aspiring developer
Profile
Posts: 469
Reg: Jan 10, 2012
Orange County, ...
13,390
like
03/06/14 10:32 PM (10 years ago)
I'm curious if what you are discussing could solve my problem (or if it's something completely different) I'm using Screen Data URL to display uploaded images, but the user needs to manually refresh the app before the new content will show up in the menu. I'm trying to get this to happen automatically when launched.
 
Niraj
buzztouch Evangelist
Profile
Posts: 2943
Reg: Jul 11, 2012
Cerritos
37,930
like
03/07/14 12:20 AM (10 years ago)
Good question, Sharon. Have to think about that one. My assumption is the images are cached for dataURLs. That should result in an auto-update for a new version of that image. However, I guess that only happens if that particular Screen was updated, then all of its corresponding images would also be updated. Try this -- use a dataURL for a particular screen. Name it myScreen. Extract out myScreen's childItems from the bt_config file and save it as a myScreen.txt file. Save that file onto a web server. Go look at the description for the simple menu plugin -- it tells you the correct format for myScreen.txt Use that file's URL as the dataURL for that Screen. Make sure the myScreen has images. Those images are referenced by URL within myScreen.txt Run the app. Does myScreen show up correctly with all the images? Now update any of the images. I bet the old image will still be showing on myScreen. If I lost the bet, then you can update images at any time and the app will show the latest version of the image. The cached image will be ignored and discarded. If I won the bet, then you need to use this trick. Update the myScreen.txt file. Remember that you already updated the image. To be sure, update a second image. Now run the app and display myScreen. It should have loaded the new version of myScreen, which should have also fetched all the images again. That refresh of myScreen causes a refresh of the childItems, which includes the images. Let us know! :-) -- Niraj
 
shenry
Aspiring developer
Profile
Posts: 469
Reg: Jan 10, 2012
Orange County, ...
13,390
like
03/10/14 12:36 PM (10 years ago)
Sorry Niraj, I'm sure it's brilliant, but I'm not following you on this.
 
Niraj
buzztouch Evangelist
Profile
Posts: 2943
Reg: Jul 11, 2012
Cerritos
37,930
like
03/10/14 05:19 PM (10 years ago)
Sharon -- there is always The Buzzcon, only a month away. Perhaps my tale will get better with age ... :-)
 
shenry
Aspiring developer
Profile
Posts: 469
Reg: Jan 10, 2012
Orange County, ...
13,390
like
03/10/14 05:40 PM (10 years ago)
Yes, can't wait!
 
Niraj
buzztouch Evangelist
Profile
Posts: 2943
Reg: Jul 11, 2012
Cerritos
37,930
like
04/29/14 08:45 PM (10 years ago)
Sharon -- do we need to re-visit this? :-)
 

Login + Screen Name Required to Post

pointerLogin to participate so you can start earning points. Once you're logged in (and have a screen name entered in your profile), you can subscribe to topics, follow users, and start learning how to make apps like the pros.