I am trying to access request object of UIWebView in webViewDidStartLoad in the following manner:
- (void) webViewDidStartLoad:(UIWebView *)webView {
NSLog(#"req : %#", [webView request]);
-----
-----
}
It displays following in console :
req : (null)
Is the above possible or I am doing something wrong?
down vote
I donot want to use it inside webView:shouldStartLoadWithRequest:)request navigationType: as this method does not get called always for goBack and goForward methods
Looks like you will still have to consider shouldStartLoadWithRequest.
Did some testing and it looks like the [webView request] is 'one step behind' in delegate methods.
This was the code:
- (BOOL)webView:(UIWebView *)webView shouldStartLoadWithRequest:(NSURLRequest *)request navigationType:(UIWebViewNavigationType)navigationType {
NSLog(#"req1a : %#", [request URL]);
NSLog(#"req1b : %#", [[webView request] URL]);
return YES;
}
- (void) webViewDidStartLoad:(UIWebView *)webView {
NSLog(#"req2 : %#", [[webView request] URL]);
}
And this were the results for initial (about:blank) and after click (some video stream, not actual printout) request:
initial request:
req1a : about:blank
req1b : (null)
req2 :
after click to a link:
req1a : xttp://origin.biokoda.tv/...
req1b : about:blank
req2 : about:blank
It looks like [webview request] is holding last loaded request.
Related
I am facing app extension close issues , please tell me if anyone know what wrong am doing.I am using action extension after preform some action inside extension i need to return response back.
Sample Code
// With Success Case
- (void) completeActionWithItems: (NSString *) response {
NSExtensionItem *extensionItem = [[NSExtensionItem alloc] init];
extensionItem.attachments = #[[[NSItemProvider alloc] response typeIdentifier: (NSString *)kUTTypePlainText]];
[self.extensionContext completeRequestReturningItems: #[extensionItem] completionHandler: nil];
}
// With Error Case
- (void) completeActionWithError: (NSError *) error {
[self.extensionContext cancelRequestWithError: error];
}
With Success Case working fine but some time is not closing,
With Error Case not working above code.
Please let me know what went wrong.Thanks
When you create an action extension, this is the default method which will close the Action Extension View Controller:
- (IBAction)done {
// Return any edited content to the host app.
// This template doesn't do anything, so we just echo the passed in items.
[self.extensionContext completeRequestReturningItems:self.extensionContext.inputItems completionHandler:nil];
}
Since this method is already provided, you should just try calling it from your success method.
// With Success Case
- (void) completeActionWithItems: (NSString *) response {
NSExtensionItem *extensionItem = [[NSExtensionItem alloc] init];
extensionItem.attachments = #[[[NSItemProvider alloc] response typeIdentifier: (NSString *)kUTTypePlainText]];
[self.extensionContext completeRequestReturningItems: #[extensionItem] completionHandler: nil];
// Call to "done" method
[self done];
}
I am implementing the CCAvenue gate way in my application.
In which CCAvenue gateway is loaded in web view from my web site.
Now after Transaction is completed with Success/Failur page,How can i came to know and load my apps success page....
Please help me Friends
The easiest way would be for your web page to send a request with a custom scheme for example myapp://transactionSuccess and your app to handle this in the webView delegate:
- (BOOL)webView:(UIWebView *)webView shouldStartLoadWithRequest:(NSURLRequest *)request navigationType:(UIWebViewNavigationType)navigationType {
NSURL *URL = [request URL];
if ([[URL scheme] isEqualToString:#"myapp"]) {
// handle the response
NSString *host = [URL host];
if ([host isEqualToString:#"transactionSuccess"]) {
// show your custom screen
return NO;
}
}
return YES;
}
Dan Spag is correct - URL Schemes make things a lot easier to manage and understand but sometimes these are just not possible. An alternative would be to ensure in the success / failure web page that in the dom (or HTML body response), the state of response is set and then capture that natively in iOS using stringByEvaluatingJavaScriptFromString like this...
- (void)webViewDidFinishLoad:(UIWebView *)webView {
NSString *responseState = [webView stringByEvaluatingJavaScriptFromString:#"document.body.innerHTML"];
// or possibly a javascript property in the webview's loaded page if preferred.
if([responseState isEqualToString:#"success"])
{
// do something with success
}
else if([responseState isEqualToString:#"fail"]) {
// do something with fail
}
[self.webView removeFromSuperView];
}
I have a problem with SoundCloud API in my application.
I have created an app, what get link to the track (e.g. something like this http://api.soundcloud.com/tracks/48760960) and get stream_url, what later can be played using SCAudioStream. There is no auth for users, I use only client id and client secret of my app. App is registered.
I create soundCloudManager this way:
- (id)init
{
if(self = [super init])
{
conf = [SCSoundCloudAPIConfiguration configurationForProductionWithClientID: kSCClientID
clientSecret: kSCClientSecret
redirectURL: kSCRedirectURL];
conf.accessTokenURL = kSCAccessTokenURL;
api = [[SCSoundCloudAPI alloc] initWithDelegate: self
authenticationDelegate: self
apiConfiguration: conf];
//[api checkAuthentication];
}
return self;
}
If uncomment [api checkAuthentication], then logs will says next:
"auth ready with URL:https://soundcloud.com/connect?client_id=&redirect_uri=&response_type=code"
Then I call this method to get data from track:
- (void)runSearchingStreamWithTrackID: (NSString *)trackID
{
[api performMethod: #"GET"
onResource: #"tracks"
withParameters: [NSDictionary dictionaryWithObject:trackID forKey:#"ids"]
context: #"trackid"
userInfo: nil];
}
And then this delegate's method calls:
- (void)soundCloudAPI:(SCSoundCloudAPI *)soundCloudAPI
didFailWithError:(NSError *)error
context:(id)context
userInfo:(id)userInfo
Text of error:
"HTTP Error: 401".
It means unauthorized. But why? Should I be authorized as soundCloud user to getting info about tracks?
I'm using this for SoundCloudAPI:
https://github.com/soundcloud/cocoa-api-wrapper
Please, help! :(
Today I fixed it. I just add this method to init :
[api authenticateWithUsername:kLogin password:kPwd];
After it this method was called:
- (void)soundCloudAPIDidAuthenticate
So, this test account was authorized.
Then I call this method:
- (void)runSearchingStreamWithTrackID: (NSString *)trackID
{
[api performMethod: #"GET"
onResource: #"tracks"
withParameters: [NSDictionary dictionaryWithObject:trackID forKey:#"ids"]
context: #"trackid"
userInfo: nil];
}
And no one of these methods will be called:
- (void)soundCloudAPI:(SCSoundCloudAPI *)soundCloudAPI
didFailWithError:(NSError *)error
context:(id)context
userInfo:(id)userInfo;
- (void)soundCloudAPI:(SCSoundCloudAPI *)soundCloudAPI
didFinishWithData:(NSData *)data
context:(id)context
userInfo:(id)userInfo;
- (void)soundCloudAPIDidAuthenticate;
- (void)soundCloudAPIDidResetAuthentication;
- (void)soundCloudAPIDidFailToGetAccessTokenWithError:(NSError *)error;
- (void)soundCloudAPIPreparedAuthorizationURL:(NSURL *)authorizationURL;
But there is log:
-[NXOAuth2PostBodyStream open] Stream has been reopened after close
And this method was called:
[NXOAuth2Client oauthConnection:connection didFailWithError:error];
error: HTTP 401
What do I wrong?
I understood the problem. Just download the SC API from the official site and install the latest SC API. Then do something like this:
- (void)searchStreamURLByTrackID: (NSString *)trackID
{
NSString *string = [NSString stringWithFormat:#"https://api.soundcloud.com/tracks/%#.json?client_id=%#", trackID, kSCClientID];
[SCRequest performMethod: SCRequestMethodGET
onResource: [NSURL URLWithString:string]
usingParameters: nil
withAccount: nil
sendingProgressHandler: nil
responseHandler:^(NSURLResponse *response, NSData *data, NSError *error){
NSString *resultString = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
NSLog(#"FOUND:\n%#", resultString);
}
];
}
After that obtain the stream url from the JSON in the resultString.
Finally, you have to write this code:
NSString *streamURL = [(NSDictionary *)jsonData objectForKey:#"stream_url"];
NSString *realURL = [streamURL stringByAppendingFormat:#".json?client_id=%#", kSCClientID];
AVPlayer *player = [[AVPlayer alloc] initWithURL:[NSURL URLWithString:realURL]];
Enjoy!
Did you check https://github.com/soundcloud/CocoaSoundCloudAPI ?
This is the more current version of the API wrapper (if you don't need iOS 3.0 support).
It also comes with a tutorial video: http://vimeo.com/28715664
If you want to stay with this library you should try to figure out where the log message ("auth ready with ...") appears. Did you implement any of the AuthorizationDelegate methods?
See https://github.com/soundcloud/cocoa-api-wrapper/blob/master/Usage.md#the-authentication-delegate-the-easy-way
I am implementing a webview based application, in that I need to find out a way when the 404 error occurred.
Anyone's help will be much appreciated.
Thanks to all,
Monish.
In the webViewDidFinishLoad method, you can also check it this way:
NSCachedURLResponse *resp = [[NSURLCache sharedURLCache] cachedResponseForRequest:webView.request];
NSLog(#"status code: %ld", (long)[(NSHTTPURLResponse*)resp.response statusCode]);
webViewDidFinishLoad() method writes following code and checks status code...
- (void)webViewDidFinishLoad:(UIWebView *)webview {
NSCachedURLResponse *urlResponse = [[NSURLCache sharedURLCache] cachedResponseForRequest:webview.request];
NSHTTPURLResponse *httpResponse = (NSHTTPURLResponse*) urlResponse.response;
NSInteger statusCode = httpResponse.statusCode;
}
Here you just need to check the status of the request when it finishes or fails in webview delegate method.`
- (void)webViewDidFinishLoad:(UIWebView *)webView
{
int status = [[[webView request] valueForHTTPHeaderField:#"Status"] intValue];
if (status == 404) {
}
}
If this doesn't help you out. Check this one.
Create an NSURLRequest with the URL you want to load. Then make the connection using NSURLConnection.
NSURLConnection has a delegate method
- (void)connection:(NSURLConnection *)connection didReceiveResponse:(NSURLResponse *)response
which will give the the response from the server. Please note that if you are making the connection over HTTP, the response will actually be of class NSHTTPURLResponse. The NSHTTPURLResponse can be used to get the status using the following instance method
- (NSInteger)statusCode
Then check if status = 404 or not and if yes then show your alert view. In this way you will be able to show the html page and the alert view both.
Try this, I think that if URL is wrong then the return html is nil. you can handle it there only
NSString *htmlCode = [[NSString alloc] initWithContentsOfURL:[NSURL URLWithString:loadUrl]];
if (htmlCode==nil)
{
// you can handle here with an alert or any message in webview to load.
}
else
{
[myWebView loadRequest:[NSURLRequest requestWithURL:[NSURL URLWithString:loadUrl]]];
}
[htmlCode release];
You can handle using htmlCode in other method like
- (void)webViewDidFinishLoad:(UIWebView *)webView
if You want to handle it after request.
Hii All,
I want to load a new page when following method is called....I am using the following code..
(void)webView:(WebView *)webView decidePolicyForNavigationAction:(NSDictionary *)actionInformation request:(NSURLRequest *)request frame:(WebFrame *)frame decisionListener:(id )listener
{
[[myWebView mainFrame] loadRequest:someRequest];
}
but this method is called multiple times and my application crashes if i use [listener use] instead of loadRequest it works fine but launches the url clicked . but i want to load some other url how is it possible?
You should simply add [listener ignore] method call.
- (void)webView:(WebView *)webView decidePolicyForNavigationAction:(NSDictionary *)actionInformation request:(NSURLRequest *)request frame:(WebFrame *)frame decisionListener:(id )listener
{
[listener ignore];
[[myWebView mainFrame] loadRequest:someRequest];
}
It's called multiple times as you say, so you have to pay attention to this:
[actionInformation valueForKey: #"WebActionNavigationTypeKey"]
That value should be one of the WebNavigationType enum:
WebNavigationTypeLinkClicked,
WebNavigationTypeFormSubmitted,
WebNavigationTypeBackForward,
WebNavigationTypeReload,
WebNavigationTypeFormResubmitted,
WebNavigationTypeOther
You will get WebNavigationTypeLinkClicked first as a result of a link clicked, and here you can decide whether to load the page clicked or something else.
Immediately after you get WebNavigationTypeOther which is the page load, and you can ignore it.
Well, in this method it is mandatory to return a value.
You're supposed to decide if you accept or not this url.
So if the WebView is going to a page you don't want,
you should return ignore.
And have the webView go to your other url: [myWebView setMainFrameURL:otherUrlStr]
Thanks