I'm having a play with the PayPal iOS SDK App which I downloaded from https://github.com/paypal/PayPal-iOS-SDK an it works beautifully in sandbox mode BUT I cannot find any property to set for the merchant email address. This is mind boggling to me, as the 'money' has to be sent to the merchant. So the question is, how is this even working?
I'm sure I'm overlooking something. Excuse the stupid question so bear with me.
Cheers.
Using the iOS SDK, the place for this information is in the PayPalConfiguration object -- it is passed as a parameter for all the PayPal provided view controllers.
So for example, in the PayPal demo app:
// Xcode 8.1, Swift 3.0
//MainViewController
//yadda yadda...
var payPalConfig = PayPalConfiguration()
// etc. etc.
override func viewDidLoad() {
super.viewDidLoad()
// Some other stuff
// Set up payPalConfig
payPalConfig.acceptCreditCards = false
payPalConfig.merchantName = "Awesome Shirts, Inc."
payPalConfig.merchantPrivacyPolicyURL = URL(string: "https://www.paypal.com/webapps/mpp/ua/privacy-full")
payPalConfig.merchantUserAgreementURL = URL(string: "https://www.paypal.com/webapps/mpp/ua/useragreement-full")
// blah blah blah
}
This config object is later passed in as:
PayPalPaymentViewController(payment: payment, configuration: payPalConfig, delegate: self)
EDIT: Correction - you're right, there is no property for the merchant's email address, even in the PayPalConfiguration object, just the merchant's name, and merchant's privacy/EULA urls.
However, it should not boggle the mind, as it were, since the merchant has a PayPal [Merchant/Business] account which will receive the money (and they certainly have the merchant's email address), and the merchant needn't expose an email address. The receiver, on the other hand, might not have a PayPal account (yet), so there are properties for the receiver's email address -- e.g., the defaultUserEmail in the configuration object, or the payeeEmail property of the PayPalPayment object (docs).
In IOS SDK, you need to update two files to reflect the environment and merchant client id.
A. ZZAppDelegate.m File
[PayPalMobile initializeWithClientIdsForEnvironments:#{PayPalEnvironmentProduction : #"YOUR_CLIENT_ID_FOR_PRODUCTION",PayPalEnvironmentSandbox : #"YOUR_CLIENT_ID_FOR_SANDBOX"}];
B. ZZMainViewController.m File
define kPayPalEnvironment PayPalEnvironmentNoNetwork
In IOS SDK, you don't need to input merchant's email address, you need to apply one client id in REST APP:https://developer.paypal.com/developer/applications, then place this clent id in above file.
Related
I have created a template in docusign web and using its template id, i am calling the function from iOS SDK.
TemplatesManager.sharedInstance.displayTemplateForSignature(templateId: templateId, controller: self, tabData: tabData, recipientData: recipientData, customFields:customFields, onlineSign: onlineSign, attachmentUrl: attachmentUrl) { (controller, errMsg) in
print(errMsg)
}
The recipient data i am sending is
let recipientDatum = DSMRecipientDefault()
// Use recipient roleName (other option to use recipient-id) to find unique recipient in the template
recipientDatum.recipientRoleName = "Client"
recipientDatum.recipientSelectorType = .recipientRoleName
recipientDatum.recipientType = .inPersonSigner
// In-person-signer name
recipientDatum.inPersonSignerName = "Akshay Somkuwar"
// Host name (must match the name on the account) and email
recipientDatum.recipientName = "Akshay Somkuwar"
recipientDatum.recipientEmail = "akshay.s.somkuwar#gmail.com"
let recipientData: Array = [recipientDatum]
Same recipient is added for template in docusign website
Also i have added observers for DSMSigningCompleted and DSMSigningCancelled to get envelopeId.
Now when i am calling this function displayTemplateForSignature no screen is opening to show the PDF or To sign the PDF, without asking for signature, the envelope is directly sent to the recipient. and i am getting this response in console with notification.
name = DSMSigningCompletedNotification, object = Optional(<Public_Adjuster.AgreementSignViewController: 0x110bb8060>), userInfo = Optional([AnyHashable("templateId"): 506346f5-7adb-4132-b15f-d288aa268398, AnyHashable("signingMode"): online, AnyHashable("envelopeId"): 2eeeeda8-5b74-4930-904e-94b2ce6451ac])
I want to open the pdf for the passed templateId but its not opening the pdf nor its asking for signature, and its directly sent to the recipient.
Any help will be appreciated, Thank you.
This behaviour, sending the envelope directly, is triggered when DocuSign SDK can not find any signers in the template/envelope that matches the logged-in user. Given that you are using the recipientDefaults, ensure that your signer information on the template (preset signer on the DocuSign web) matches the Account information exactly with the recipientDefaults object.
You may compare it with .
One issue I noticed is the signer type is set to need to sign which corresponds to a remoteSigner on the DocuSign web. And on the recipientDefaults object it's set as inPersonSigner. It should be .signer corresponding to DSMRecipientTypeSigner.
recipientDatum.recipientType = .signer.
Or you may change the need to sign to in person signer on the DocuSign web.
Another suggestion is to remove the name & email from the template screenshot shared and keep that empty as the client app is passing name & email with the recipientDefaults object to the SDK.
More details: How to set recipient defaults
I have a webapp and the iOS app built in Swift. The thing is I don't know Swift and I'm trying to modify the iOS app in order to add the authorization key to the PubNub client before subscribing/publishing to channels.
Link to PubNub docs
PRE:
Access Manager is enabled
my_auth_key is hardcoded and already enabled form the server for the corresponding channel I want to subscribe.
Here is the code
What's the correct way to set the auth key?
Thanks in advance
Polak, mentioned docs code snippet refer to previously created instance to get it's pre-configured PNConfiguration instance and change required field. This practice can be used in case if you need change something at run-time.
If you have data for authKey at the moment of client initialization, you can set it:
var pubnubClient: PubNub = {
let configuration = PNConfiguration(publishKey: UCConstants.PubNub.publishKey, subscribeKey: UCConstants.PubNub.subscribeKey)
configuration.authKey = "my_auth_key"
return PubNub.clientWithConfiguration(configuration)
}()
Also, I've tried exact your code and don't have any issues with setting of authKey, because I can see it with subscribe request.
If you still will have troubles with PAM and auth key usage, please contact us on support#pubnub.com
Looks like you can:
let configuration = PNConfiguration(
authKey: "super_secret",
publishKey: UCConstants.PubNub.publishKey,
subscribeKey: UCConstants.PubNub.subscribeKey
)
Based on the Obj-C code: https://github.com/pubnub/objective-c/blob/8c1f0876b5b34176f33681d22844e8d763019635/PubNub/Data/PNConfiguration.m#L174-L181
Hopefully the title is self-explanatory. I'm trying to do something like this:
checkIfUserIsSubscribedToProduct(productID, transactionID: "some-unique-transaction-string", completion: { error, status in
if error == nil {
if status == .Subscribed {
// do something fun
}
}
}
does anything like the hypothetical code I've provided exist? I feel like I'm taking crazy pills
Edit
In similar questions I keep seeing a generic answer of "oh you gotta validate the receipt" but no explanation on how, or even what a receipt is. Could someone provide me with how to "validate the receipt"? I tried this tutorial but didn't seem to work.
Edit - For Bounty
Please address the following situation: A user subscribes to my auto-renewable subscription and gets more digital content because of it - cool, implemented. But how do I check whether that subscription is still valid (i.e. they did not cancel their subscription) each time they open the app? What is the simplest solution to check this? Is there something like the hypothetical code I provided in my question? Please walk me through this and provide any further details on the subject that may be helpful.
I know everyone was very concerned about me and how I was doing on this - fear not, solved my problem. Main problem was that I tried Apple's example code from the documentation, but it wasn't working so I gave up on it. Then I came back to it and implemented it with Alamofire and it works great. Here's the code solution:
Swift 3:
let receiptURL = Bundle.main.appStoreReceiptURL
let receipt = NSData(contentsOf: receiptURL!)
let requestContents: [String: Any] = [
"receipt-data": receipt!.base64EncodedString(options: []),
"password": "your iTunes Connect shared secret"
]
let appleServer = receiptURL?.lastPathComponent == "sandboxReceipt" ? "sandbox" : "buy"
let stringURL = "https://\(appleServer).itunes.apple.com/verifyReceipt"
print("Loading user receipt: \(stringURL)...")
Alamofire.request(stringURL, method: .post, parameters: requestContents, encoding: JSONEncoding.default)
.responseJSON { response in
if let value = response.result.value as? NSDictionary {
print(value)
} else {
print("Receiving receipt from App Store failed: \(response.result)")
}
}
As some comments pointed out there's a couple flaws with these answers.
Calling /verifyReceipt from the client isn't secure.
Comparing expiration dates against the device clock can be spoofed by changing the time (always a fun hack to try after cancelling a free trial :) )
There are some other tutorials of how to set up a server to handle the receipt verification, but this is only part of the problem. Making a network request to unpack and validate a receipt on every app launch can lead to issues, so there should be some caching too to keep things running smoothly.
The RevenueCat SDK provides a good out-of-the box solution for this.
A couple reasons why I like this approach:
Validates receipt server side (without requiring me to set up a server)
Checks for an "active" subscription with a server timestamp so can't be spoofed by changing the device clock
Caches the result so it's super fast and works offline
There's some more details in this question: https://stackoverflow.com/a/55404121/3166209
What it works down to is a simple function that you can call as often as needed and will return synchronously in most cases (since it's cached).
subscriptionStatus { (subscribed) in
if subscribed {
// Show that great pro content
}
}
What are you trying to achieve in particular? Do you want to check for a specific Apple ID?
I highly doubt that this is possible through the SDK. Referring to Is it possible to get the user's apple ID through the SDK? you can see that you can't even ask for the ID directly but rather services attached to it.
What would work is caching all transactions on your own server and search its database locally but that would require the app to ask for the user's Apple ID so the app could update the subscription state whenever it launches as it can check for IAP of the ID associated with the device.
However, the user could just type whatever he wanted - and it's unlikely to get this through Apple's app review process.
I am using MKSoreKit https://github.com/MugunthKumar/MKStoreKit for auto-renew subscriptions.but it is in objective c you can check the library code for solution.I am using it in my code and it is working fine.
using below method you can easily check subscription status..
if([MKStoreManager isProductPurchased:productIdentifier]) {
//unlock it
}
It gets the apple id from device and I think that is user specific
This is what I used to register the phone number with Account Kit
- (void)viewDidLoad{
[super viewDidLoad];
// initialize Account Kit
if (_accountKit == nil) {
// may also specify AKFResponseTypeAccessToken
_accountKit = [[AKFAccountKit alloc] initWithResponseType:AKFResponseTypeAuthorizationCode];
}
// view controller for resuming login
_pendingLoginViewController = [_accountKit viewControllerForLoginResume];
}
I have implemented Account kit using Swift. I have implemented to register the phone number, but I was wondering if I could detect if the phone is already registered within this the app.
You can check if somebody is already logged in like this:
https://developers.facebook.com/docs/accountkit/ios#loginview
You can store the phone numbers and accountIDs in your own user tables to also verify if somebody has already created an account with that information. You can call the GraphAPI (https://developers.facebook.com/docs/accountkit/graphapi) from your server to check if there have been any updates to those accounts.
i build a register form for my app and i need to send the user a verifiation code by sms in order to complete the registration proccess.
i tried to use MFMessageComposeViewController but its open the dialog sms on the device so the user can see the code.
i also checked the web for 3party of sending sms but there is a problem with the country code. i know its posible becuse whatsapp do it to confirm the user.
what it the right way to do it?
this is the topic the i tried:
Sending SMS in iOS with Swift
The best way to achieve this is by creating some views for allowing the user to enter the phone number with the country code which can be used by a server to send a request for initiating the OTP verification. To achieve this you need to:
Create View Controllers.
Upload Phone Number and Country code to the server.
Validate the requests by verifying the OTP.
As mentioned by Dan, you can use Digits in Fabric for that purpose, and create custom views for a great UX.
On the other hand, you can also use a service called as SendOTP from MSG91 - you can use it for internal testing and development ideas as they provide you with 5,000 free OTP SMS. The service has a complete set of APIs which you can implement on the backend as well on the app front. Also, they provide a framework so that you don't need to create the views, but only presentViewController and call delegate methods for knowing what happened during the verification process - such as Cancelled or Verified or Failed.
Swift implementation of the same looks like this:
class OTPFrame: UIViewController, sendOTPAuthenticationViewControllerDelegate {
func loadOTPFramework() {
SendOTP.sharedManager().startWithApiId("yourAppID")
let frameworkPath: NSString = NSBundle.mainBundle().privateFrameworksPath!
let frameworkBundlePath: NSString = frameworkPath.stringByAppendingPathComponent("SendOTPFramework.framework")
let frameworkBundle : NSBundle
= NSBundle(path: frameworkBundlePath as String)!
let authenticationViewController: AuthenticationViewController = AuthenticationViewController(nibName: "AuthenticationViewController", bundle: frameworkBundle)
authenticationViewController.delegate = self self.presentViewController(authenticationViewController, animated: true, completion: nil)
}
func authenticationisSuccessfulForMobileNumber(mobNo: String!, withCountryCode countryCode: String!) {
print("Success")
}
func canceledAuthentication() {
print("Cancelled")
}
func authenticationisFailedForMobileNumber(mobNo: String!, withCountryCode countryCode: String!) {
print("Failed")
}
}
Disclaimer: I, in no way, endorse the services mentioned above - you are free to choose whatever you like.
Thank You!
I would give digits a try! It's part of the Twitter Fabric package and it's very simple to use. The user enters their phone number and Fabric takes care of validating the number.