Edit 23.5.11
I'm now wondering whether I'm over engineering this. When I use an online connection, I handle it properly - either:
in the background with a progress or activity indicator showing and if it fails, I display a suitable message OR
I call another application, either Safari or Maps which will then do its own check and fail if there is no connection. That leaves the user in that other app that has failed, which is not perfect tho.
So if I do what I'm suggesting below and standard Reachability returns not reachable and I then have to do a NSURLConnection in case the radios have gone to sleep, then I'm not sure that's any better than just trying to get the online resource in the first place.
If anyone can help - I'd be really grateful. I'm almost ready to submit, just need to get this right.
I'm using Apple's Reachability sample to generally good effect except for when the mobile or cellular connection goes to sleep and then comes back or the wifi goes and the cellular connection is then relied on.
Its fine when the mobile (cellular) connection isn't changing. This is in line with comments I've read, that when the cellular radio switches off you have to wake it up again manually. However, I can't see how to do that.
Do I need to setup a NSURLConnection? Some sample code would be great. When I get a notification that there is no connection, would I send the NSURLConnection and tell the user to try again in a moment and then if I get a callback to say its successful, override the off setting from Reachability?
In addition, would I need to do that whenever there seems to be no connection, just in case its that - this seems wasteful of resources when it may well not be that. e.g.an iPod Touch that's not in wifi reach.
I've also looked at DDG's alternative, but it looks like that will have the same issue.
Any helpful suggestions would be warmly welcomed.
Thanks,
Chris.
You cannot and should not use Apple's Reachabilty sample code (or the SCNetworkReachabilityFlags) to determine if a network resource is or will be available. They give you useful tools for giving user feedback about why a connection failed and for determining if and when to retry a connection. However if you want to access a network resource you should just ask for it.
Don't present your users with "no network connection" alerts based on the reachability flags. Perform your network request and if it fails check the reachability flags and your own history of requests to see if you should tell your user that the request failed or silently retry. You shouldn't want or need to spam the user with every network failure. If a request fails consider retrying it if the host seems to be reachable and only report a failure to the user after a couple of attempts or when the reachability flags suggest that you have actually lost your network connection and not just had a single request fail.
As for reactivating the device's radios you'll need to balance your desire to try to fetch network resources with allowing the device to power down the network interfaces to save power. I don't know what your app is trying to do but I'd recommend allowing the device to power down and then trying to connect in response to a user asking the app to fetch new data. I don't see a case where you would want to reactivate a radio just to give the user a hint that some network resource may or may not currently be reachable.
See https://devforums.apple.com/message/409618
The only way to know whether a host is available is to try to connect to it. If that connection fails, you can use reachability to provide feedback to the user, and to guide your retry mechanism, but using reachability to preflight a connection is not a good idea.
The key issue here is that reachability uses local information to determine its results. This doesn't say anything about the state of the wider Internet. The origin server might be down, or any number of links between you and the origin server might be down, and reachability will happily say that it's reachable. At that point you're going to try to connect, and the connection will fail. So you're going to have to handle the error anyway, which means you might as well not do the preflight and let your standard error handling cover this case as well.
Also take a look at this question regarding checking for a resource before loading it using an external application: https://devforums.apple.com/message/411329
Making a HEAD request for the resource should give you a reasonable idea if the external app will be able to load it without requiring you to download a significant amount of data (latency will still be a concern though).
Related
I am making a macos app in XCode, and I was wondering if there was a way to make it host a local server that is visible across the network.
I am trying to find a way so that it would host something on the devices's network with it's hostname/ip address, so if someone goes to http://hostname:5000 they would be able to see the response, and the app would be able to see the request, just like how hosting a local python server works. Is there any way to do this in XCode with Swift?
For example: the user presses 'start server' on their screen. The server is hosted across the network. Anytime a request is made to it, they get a notification.
Just to make you concern you may find some sample codes, including local web server inside the app.Few of them I found are:
https://github.com/ooper-shlab/MyWebViewApp-Swift
https://github.com/depoon/SwiftLocalhost
The main thing is it's just a public
, experimental code, so it's not simple, not easy to adopt, not all coding best-recommended, far from readable and may have severe bugs.But you can use it as a working example and take any parts of it into your app.
I am getting many welcome messages from the same user, is it some kind of a monitoring system by Google?
How can I learn to ignore those requests?
Yes, Google periodically issues a health check against your Action, usually about every 5-10 minutes. Your Action should respond to it normally so Google knows if there is something wrong. If there is, you will receive email that your Action is unavailable because it is unhealthy. They will continue to monitor it and, when healthy again, will restore it.
You don't need to ignore those requests, however you may wish to, either to save on resources or to avoid logging it all the time.
With a library such as multivocal, it detects it and responds automatically - there is nothing you need to to. For other libraries, you will need to examine the raw input sent in the body of your webhook request.
If you are using the Action SDK, you should examine the inputs array to see if there is one with an argument named "is_health_check". If you are using Dialogflow, then you would need to look under originalDetectIntentRequest.data.inputs.
I have a lobby in which I want the users to be in sync. So when a user turns off his internet while the app is running, he should be removed. I know Firebase does not support server side coding, so the coding needs to be client side. The answers from How to delete firebase data after "n" days and Delete firebase data older than 2 hours do not answer this question since they expect that the user is online and they have an internet connection. So my question is if is possible to delete users when they got no internet? I thought maybe it is an idea to let the users update a value every 5 seconds, and when that update is not done, the other users in that lobby remove the player. This way is not good, since every player needs to retrieve and upload alot of data every 5 seconds. What is the best way to solve this?
Edit: to make it short, lets say each user has an image. The image should be green when the user is connected, and grey when disconnected.
Edit 2: after thinking it over, it is really hard to accurate present the connected users on a client-side server. That is why, if nobody has a different solution, I should add another server which can execute server-side codes. Because of the larges amount of servers, I would like to know which server I should use. The server should run a simple function which only checks if the users are connected or disconnected and can communicate with Firebase. If I am correct it should look like this:
But the server also needs to communicate with the users directly. I have absoluty no idea where to start.
If I'm not completely wrong, you should be able to use onDisconnect.
From the Firebase, documentation:
How onDisconnect:Works:
When an onDisconnect() operation is established, it lives on the Firebase Realtime Database server. The server checks security to make sure the user can perform the write event requested, and informs the client if it is invalid. The server then monitors the connection. If at any point it times out, or is actively closed by the client, the server checks security a second time (to make sure the operation is still valid) and then invokes the event.
In app in production I'm using onDisconnectRemoveValue, and when I close the app, the user removes himself from the lobby. Not sure how it works when you turn the device in airplane mode, but from the documentation it seems there should be no problem.
One thing: when you test it better do it on real device, the simulator have issues with turning it off and on, at least the on I have installed.
Edit: So i checked the onDisconnect when you put the device on airplane mode and it works! The question is, that it removes the user in about a 1:30 min, approximately, so if you read the documentation or ask the support, you may be (and only may be) able to find a way to set the time you want.
I am trying to write a VPN app using VpnService. I started my app based on the sample ToyVpn. It seems to work fine but I am wondering if there is a way to get rid of the pop up dialog when I click connect. I am hoping that I could just click "connect" and it would start without having to click the "I trust this application..." check box and "Ok".
Thanks.
I don't think it's possible. They seem to be very careful about this class. If you take a look at the documentation you can see it says:
Letting applications intercept packets raises huge security concerns. A VPN application can easily break the network. Besides, two of them may conflict with each other. The system takes several actions to address these issues. Here are some key points:
User action is required to create a VPN connection. [emphasis mine]
There can be only one VPN connection running at the same time. The existing interface is deactivated when a new one is created.
A system-managed notification is shown during the lifetime of a VPN connection.
A system-managed dialog gives the information of the current VPN connection. It also provides a button to disconnect.
The network is restored automatically when the file descriptor is closed. It also covers the cases when a VPN application is crashed or killed by the system.
Since it says that user action is required to create the VPN connection, I assume they mean this is something you cannot control yourself.
I read a few tutorials / howtos about Apples Push Notifications, but there are a lot of information out there, so I wanna know if I understand everything correct.
Here is how I understand it:
You need a certificate for Puhs, you can get it in the development center (found very good tutorials for it)
You need a database in which the DeviceToken is stored. This you can set into the database from your application itself (found a tutorial for that I think)
When a user should get a message (e.g. gets a Private Message or something like this) you must send a PHP Payload to the apple server.
Is that all? (I know its a much longer, I only wanna know if I understand everything right).
Must I do any other thing on the client side else then save the device token to the database?
Yes you pretty much have it there. If looking at sending large volumes then make sure that you are not opening and closing the connection to the Apple APNS servers as they treat it as a DOS attack.
The payload is also not PHP but JSON.
Also make sure you read from the feedback service and deactivated device tokens and stop sending them messages.
Client side you also need to "decode/process" the payload in the various app delegate places. Essentially it is a discretionary and you can send custom info as part of the APNS payload.