Bläddra i källkod

Updated view controllers and storyboards with verifyPurchase actions and alerts

Andrea Bizzotto 9 år sedan
förälder
incheckning
9d15648d88

+ 26 - 18
SwiftyStoreDemo/Base.lproj/Main.storyboard

@@ -1,8 +1,8 @@
 <?xml version="1.0" encoding="UTF-8" standalone="no"?>
-<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="9531" systemVersion="14F27" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" initialViewController="BYZ-38-t0r">
+<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="10117" systemVersion="15E65" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" initialViewController="BYZ-38-t0r">
     <dependencies>
         <deployment identifier="iOS"/>
-        <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="9529"/>
+        <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="10085"/>
     </dependencies>
     <scenes>
         <!--View Controller-->
@@ -22,22 +22,7 @@
                             </imageView>
                             <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="R2x-3P-rjx" userLabel="Opaque">
                                 <rect key="frame" x="0.0" y="0.0" width="600" height="600"/>
-                                <subviews>
-                                    <button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="roundedRect" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="Hpv-ED-Dlg">
-                                        <rect key="frame" x="233" y="391" width="135" height="36"/>
-                                        <fontDescription key="fontDescription" type="boldSystem" pointSize="20"/>
-                                        <state key="normal" title="Verify Receipt">
-                                            <color key="titleColor" white="1" alpha="1" colorSpace="calibratedWhite"/>
-                                        </state>
-                                        <connections>
-                                            <action selector="verifyReceipt" destination="BYZ-38-t0r" eventType="touchUpInside" id="61I-gF-E2O"/>
-                                        </connections>
-                                    </button>
-                                </subviews>
                                 <color key="backgroundColor" red="0.0" green="0.0" blue="0.0" alpha="0.29999999999999999" colorSpace="custom" customColorSpace="sRGB"/>
-                                <constraints>
-                                    <constraint firstItem="Hpv-ED-Dlg" firstAttribute="centerX" secondItem="R2x-3P-rjx" secondAttribute="centerX" id="Zsj-pM-1iO"/>
-                                </constraints>
                             </view>
                             <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="SwiftyStoreKit" textAlignment="center" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="FTs-3H-z8C">
                                 <rect key="frame" x="218" y="40" width="163" height="33"/>
@@ -196,12 +181,32 @@
                                     <action selector="restorePurchases" destination="BYZ-38-t0r" eventType="touchUpInside" id="ulP-6V-3dz"/>
                                 </connections>
                             </button>
+                            <button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="roundedRect" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="Hpv-ED-Dlg">
+                                <rect key="frame" x="232" y="391" width="135" height="36"/>
+                                <fontDescription key="fontDescription" type="boldSystem" pointSize="20"/>
+                                <state key="normal" title="Verify Receipt">
+                                    <color key="titleColor" white="1" alpha="1" colorSpace="calibratedWhite"/>
+                                </state>
+                                <connections>
+                                    <action selector="verifyReceipt" destination="BYZ-38-t0r" eventType="touchUpInside" id="61I-gF-E2O"/>
+                                </connections>
+                            </button>
+                            <button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="roundedRect" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="TLr-vr-TSi">
+                                <rect key="frame" x="224" y="435" width="152" height="36"/>
+                                <fontDescription key="fontDescription" type="boldSystem" pointSize="20"/>
+                                <state key="normal" title="Verify Purchase">
+                                    <color key="titleColor" white="1" alpha="1" colorSpace="calibratedWhite"/>
+                                </state>
+                                <connections>
+                                    <action selector="verifyPurchase" destination="BYZ-38-t0r" eventType="touchUpInside" id="jeM-Kt-Lpj"/>
+                                </connections>
+                            </button>
                         </subviews>
                         <color key="backgroundColor" white="1" alpha="1" colorSpace="custom" customColorSpace="calibratedWhite"/>
                         <constraints>
-                            <constraint firstItem="Hpv-ED-Dlg" firstAttribute="top" secondItem="CG8-Ue-vcg" secondAttribute="bottom" constant="8" id="1yX-Os-AKT"/>
                             <constraint firstItem="FII-Z2-VOo" firstAttribute="top" secondItem="s8k-6i-mKn" secondAttribute="bottom" constant="30" id="4jU-Ih-evH"/>
                             <constraint firstItem="FII-Z2-VOo" firstAttribute="top" secondItem="y3c-jy-aDJ" secondAttribute="bottom" constant="50" id="5RH-5E-DHg"/>
+                            <constraint firstItem="TLr-vr-TSi" firstAttribute="top" secondItem="Hpv-ED-Dlg" secondAttribute="bottom" constant="8" id="Dxo-97-Yvh"/>
                             <constraint firstAttribute="trailing" secondItem="JDz-7n-4vD" secondAttribute="trailing" id="GBV-Mt-YQc"/>
                             <constraint firstItem="JDz-7n-4vD" firstAttribute="top" secondItem="8bC-Xf-vdC" secondAttribute="top" id="GlE-OZ-BQY"/>
                             <constraint firstAttribute="trailing" secondItem="gg1-bw-Mzz" secondAttribute="trailing" constant="10" id="HVm-oI-bi4"/>
@@ -212,6 +217,7 @@
                             <constraint firstItem="CG8-Ue-vcg" firstAttribute="centerX" secondItem="8bC-Xf-vdC" secondAttribute="centerX" id="U3y-1n-HiO"/>
                             <constraint firstItem="R2x-3P-rjx" firstAttribute="leading" secondItem="8bC-Xf-vdC" secondAttribute="leading" id="U9f-il-AMN"/>
                             <constraint firstItem="wfy-db-euE" firstAttribute="top" secondItem="JDz-7n-4vD" secondAttribute="bottom" id="Uxb-Hz-CCC"/>
+                            <constraint firstItem="Hpv-ED-Dlg" firstAttribute="top" secondItem="CG8-Ue-vcg" secondAttribute="bottom" constant="8" id="WJS-4L-FPg"/>
                             <constraint firstItem="gg1-bw-Mzz" firstAttribute="top" secondItem="FTs-3H-z8C" secondAttribute="bottom" constant="2" id="X0K-RO-cp1"/>
                             <constraint firstItem="CG8-Ue-vcg" firstAttribute="top" secondItem="FII-Z2-VOo" secondAttribute="bottom" constant="40" id="ZEX-Nc-VGE"/>
                             <constraint firstItem="JDz-7n-4vD" firstAttribute="leading" secondItem="8bC-Xf-vdC" secondAttribute="leading" id="eKg-Cq-0M3"/>
@@ -219,6 +225,8 @@
                             <constraint firstItem="s8k-6i-mKn" firstAttribute="centerX" secondItem="8bC-Xf-vdC" secondAttribute="centerX" id="kNl-ka-qbp"/>
                             <constraint firstItem="gg1-bw-Mzz" firstAttribute="leading" secondItem="8bC-Xf-vdC" secondAttribute="leading" constant="10" id="lx2-KO-4yZ"/>
                             <constraint firstItem="FTs-3H-z8C" firstAttribute="top" secondItem="y3c-jy-aDJ" secondAttribute="bottom" constant="20" id="paF-3I-iVD"/>
+                            <constraint firstItem="TLr-vr-TSi" firstAttribute="centerX" secondItem="8bC-Xf-vdC" secondAttribute="centerX" id="q4v-bD-EYb"/>
+                            <constraint firstItem="Hpv-ED-Dlg" firstAttribute="centerX" secondItem="8bC-Xf-vdC" secondAttribute="centerX" id="t1X-dA-gke"/>
                             <constraint firstItem="FII-Z2-VOo" firstAttribute="centerX" secondItem="8bC-Xf-vdC" secondAttribute="centerX" id="x6e-Ni-abV"/>
                         </constraints>
                         <variation key="default">

+ 46 - 7
SwiftyStoreDemo/ViewController.swift

@@ -32,22 +32,22 @@ class ViewController: UIViewController {
     
     // MARK: actions
     @IBAction func getInfo1() {
-        getInfo("1")
+        getInfo("purchase1")
     }
     @IBAction func getInfo2() {
-        getInfo("2")
+        getInfo("consumablePurchase")
     }
     @IBAction func purchase1() {
-        purchase("1")
+        purchase("purchase1")
     }
     @IBAction func purchase2() {
-        purchase("2")
+        purchase("consumablePurchase")
     }
     
     func getInfo(no: String) {
         
         NetworkActivityIndicatorManager.networkOperationStarted()
-        SwiftyStoreKit.retrieveProductsInfo([AppBundleId + ".purchase" + no]) { result in
+        SwiftyStoreKit.retrieveProductsInfo([AppBundleId + "." + no]) { result in
             NetworkActivityIndicatorManager.networkOperationFinished()
             
             self.showAlert(self.alertForProductRetrievalInfo(result))
@@ -57,7 +57,7 @@ class ViewController: UIViewController {
     func purchase(no: String) {
         
         NetworkActivityIndicatorManager.networkOperationStarted()
-        SwiftyStoreKit.purchaseProduct(AppBundleId + ".purchase" + no) { result in
+        SwiftyStoreKit.purchaseProduct(AppBundleId + "." + no) { result in
             NetworkActivityIndicatorManager.networkOperationFinished()
             
             self.showAlert(self.alertForPurchaseResult(result))
@@ -88,6 +88,31 @@ class ViewController: UIViewController {
             }
         }
     }
+    
+    @IBAction func verifyPurchase() {
+     
+        NetworkActivityIndicatorManager.networkOperationStarted()
+        SwiftyStoreKit.verifyReceipt() { result in
+            NetworkActivityIndicatorManager.networkOperationFinished()
+            
+            switch result {
+            case .Success(let receipt):
+                
+                let purchaseResult = SwiftyStoreKit.verifyPurchase(
+                    productId: self.AppBundleId + "consumablePurchase",
+                    inReceipt: receipt,
+                    validUntil: NSDate()
+                )
+                self.showAlert(self.alertForVerifyPurchase(purchaseResult))
+                
+            case .Error(let error):
+                self.showAlert(self.alertForVerifyReceipt(result))
+                if case .NoReceiptData = error {
+                    self.refreshReceipt()
+                }
+            }
+        }
+    }
 
     func refreshReceipt() {
 
@@ -174,7 +199,7 @@ extension ViewController {
     }
 
 
-    func alertForVerifyReceipt(result: SwiftyStoreKit.VerifyReceiptResult) -> UIAlertController{
+    func alertForVerifyReceipt(result: SwiftyStoreKit.VerifyReceiptResult) -> UIAlertController {
 
         switch result {
         case .Success(let receipt):
@@ -189,7 +214,21 @@ extension ViewController {
                 return alertWithTitle("Receipt verification", message: "Receipt verification failed")
             }
         }
+    }
 
+    func alertForVerifyPurchase(result: SwiftyStoreKit.VerifyPurchaseResult) -> UIAlertController {
+        
+        switch result {
+        case .Purchased(let expiresDate):
+            if let expiresDate = expiresDate {
+                return alertWithTitle("Product is purchased", message: "Product is valid until \(expiresDate)")
+            }
+            return alertWithTitle("Product is purchased", message: "Product will not expire")
+        case .Expired(let expiresDate): // Only for Automatically Renewable Subscription
+            return alertWithTitle("Product expired", message: "Product is expired since \(expiresDate)")
+        case .NotPurchased:
+            return alertWithTitle("Not purchased", message: "This product has never been purchased")
+        }
     }
 
     func alertForRefreshReceipt(result: SwiftyStoreKit.RefreshReceiptResult) -> UIAlertController {

+ 29 - 17
SwiftyStoreOSXDemo/Base.lproj/Main.storyboard

@@ -1,7 +1,7 @@
 <?xml version="1.0" encoding="UTF-8" standalone="no"?>
-<document type="com.apple.InterfaceBuilder3.Cocoa.Storyboard.XIB" version="3.0" toolsVersion="9531" systemVersion="15B42" targetRuntime="MacOSX.Cocoa" propertyAccessControl="none" useAutolayout="YES" initialViewController="B8D-0N-5wS">
+<document type="com.apple.InterfaceBuilder3.Cocoa.Storyboard.XIB" version="3.0" toolsVersion="10117" systemVersion="15E65" targetRuntime="MacOSX.Cocoa" propertyAccessControl="none" useAutolayout="YES" initialViewController="B8D-0N-5wS">
     <dependencies>
-        <plugIn identifier="com.apple.InterfaceBuilder.CocoaPlugin" version="9531"/>
+        <plugIn identifier="com.apple.InterfaceBuilder.CocoaPlugin" version="10117"/>
     </dependencies>
     <scenes>
         <!--Application-->
@@ -673,7 +673,7 @@
                         <autoresizingMask key="autoresizingMask"/>
                         <subviews>
                             <button verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="4ix-eb-y5G">
-                                <rect key="frame" x="163" y="48" width="154" height="32"/>
+                                <rect key="frame" x="163" y="73" width="154" height="32"/>
                                 <buttonCell key="cell" type="push" title="Restore Purchases" bezelStyle="rounded" alignment="center" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="mmO-hG-Xyq">
                                     <behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
                                     <font key="font" metaFont="system"/>
@@ -682,17 +682,17 @@
                                     </connections>
                                 </buttonCell>
                             </button>
-                            <customView translatesAutoresizingMaskIntoConstraints="NO" id="aBh-sv-MN6">
-                                <rect key="frame" x="0.0" y="84" width="480" height="176"/>
+                            <customView misplaced="YES" translatesAutoresizingMaskIntoConstraints="NO" id="aBh-sv-MN6">
+                                <rect key="frame" x="0.0" y="121" width="480" height="139"/>
                                 <subviews>
-                                    <splitView focusRingType="none" dividerStyle="thin" vertical="YES" translatesAutoresizingMaskIntoConstraints="NO" id="dZR-88-4H6">
-                                        <rect key="frame" x="0.0" y="0.0" width="480" height="176"/>
+                                    <splitView focusRingType="none" misplaced="YES" dividerStyle="thin" vertical="YES" translatesAutoresizingMaskIntoConstraints="NO" id="dZR-88-4H6">
+                                        <rect key="frame" x="0.0" y="-37" width="480" height="176"/>
                                         <subviews>
-                                            <customView id="rDg-4M-vFs">
+                                            <customView misplaced="YES" id="rDg-4M-vFs">
                                                 <rect key="frame" x="0.0" y="0.0" width="254" height="176"/>
                                                 <autoresizingMask key="autoresizingMask"/>
                                                 <subviews>
-                                                    <button verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="ypp-fu-oEb">
+                                                    <button verticalHuggingPriority="750" misplaced="YES" translatesAutoresizingMaskIntoConstraints="NO" id="ypp-fu-oEb">
                                                         <rect key="frame" x="83" y="103" width="89" height="32"/>
                                                         <buttonCell key="cell" type="push" title="Get Info" bezelStyle="rounded" alignment="center" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="vSi-fu-wrI">
                                                             <behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
@@ -702,7 +702,7 @@
                                                             <action selector="getInfo1:" target="XfG-lQ-9wD" id="PTC-RY-Aom"/>
                                                         </connections>
                                                     </button>
-                                                    <textField horizontalHuggingPriority="251" verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="23w-eX-lGC">
+                                                    <textField horizontalHuggingPriority="251" verticalHuggingPriority="750" misplaced="YES" translatesAutoresizingMaskIntoConstraints="NO" id="23w-eX-lGC">
                                                         <rect key="frame" x="105" y="139" width="44" height="17"/>
                                                         <textFieldCell key="cell" scrollable="YES" lineBreakMode="clipping" sendsActionOnEndEditing="YES" title="5 days" id="U2h-U7-cdn">
                                                             <font key="font" metaFont="system"/>
@@ -710,7 +710,7 @@
                                                             <color key="backgroundColor" name="controlColor" catalog="System" colorSpace="catalog"/>
                                                         </textFieldCell>
                                                     </textField>
-                                                    <button verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="Hez-z0-TRG">
+                                                    <button verticalHuggingPriority="750" misplaced="YES" translatesAutoresizingMaskIntoConstraints="NO" id="Hez-z0-TRG">
                                                         <rect key="frame" x="79" y="70" width="97" height="32"/>
                                                         <buttonCell key="cell" type="push" title="Purchase" bezelStyle="rounded" alignment="center" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="5bl-kX-gwW">
                                                             <behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
@@ -730,11 +730,11 @@
                                                     <constraint firstItem="ypp-fu-oEb" firstAttribute="centerX" secondItem="rDg-4M-vFs" secondAttribute="centerX" id="jeS-t3-Km1"/>
                                                 </constraints>
                                             </customView>
-                                            <customView id="ecz-ZL-FwI">
+                                            <customView misplaced="YES" id="ecz-ZL-FwI">
                                                 <rect key="frame" x="255" y="0.0" width="225" height="176"/>
                                                 <autoresizingMask key="autoresizingMask"/>
                                                 <subviews>
-                                                    <textField horizontalHuggingPriority="251" verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="gj2-Z2-1qo">
+                                                    <textField horizontalHuggingPriority="251" verticalHuggingPriority="750" misplaced="YES" translatesAutoresizingMaskIntoConstraints="NO" id="gj2-Z2-1qo">
                                                         <rect key="frame" x="88" y="139" width="50" height="17"/>
                                                         <textFieldCell key="cell" scrollable="YES" lineBreakMode="clipping" sendsActionOnEndEditing="YES" title="10 days" id="XkC-cw-jpP">
                                                             <font key="font" metaFont="system"/>
@@ -742,7 +742,7 @@
                                                             <color key="backgroundColor" name="controlColor" catalog="System" colorSpace="catalog"/>
                                                         </textFieldCell>
                                                     </textField>
-                                                    <button verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="32D-7s-IOR">
+                                                    <button verticalHuggingPriority="750" misplaced="YES" translatesAutoresizingMaskIntoConstraints="NO" id="32D-7s-IOR">
                                                         <rect key="frame" x="68" y="103" width="89" height="32"/>
                                                         <buttonCell key="cell" type="push" title="Get Info" bezelStyle="rounded" alignment="center" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="F8O-DF-BZX">
                                                             <behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
@@ -752,7 +752,7 @@
                                                             <action selector="getInfo2:" target="XfG-lQ-9wD" id="u4g-Qb-RyE"/>
                                                         </connections>
                                                     </button>
-                                                    <button verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="GkW-aD-XKc">
+                                                    <button verticalHuggingPriority="750" misplaced="YES" translatesAutoresizingMaskIntoConstraints="NO" id="GkW-aD-XKc">
                                                         <rect key="frame" x="64" y="70" width="97" height="32"/>
                                                         <buttonCell key="cell" type="push" title="Purchase" bezelStyle="rounded" alignment="center" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="TDW-1n-a4d">
                                                             <behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
@@ -795,7 +795,7 @@
                                 </textFieldCell>
                             </textField>
                             <button verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="Yzl-nj-7ol">
-                                <rect key="frame" x="178" y="15" width="125" height="32"/>
+                                <rect key="frame" x="178" y="40" width="125" height="32"/>
                                 <buttonCell key="cell" type="push" title="Verify Receipt" bezelStyle="rounded" alignment="center" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="6bY-Fv-W6P">
                                     <behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
                                     <font key="font" metaFont="system"/>
@@ -804,9 +804,19 @@
                                     <action selector="verifyReceipt:" target="XfG-lQ-9wD" id="uf9-Pe-MRz"/>
                                 </connections>
                             </button>
+                            <button verticalHuggingPriority="750" translatesAutoresizingMaskIntoConstraints="NO" id="NrD-IB-ZDO">
+                                <rect key="frame" x="172" y="7" width="136" height="32"/>
+                                <buttonCell key="cell" type="push" title="Verify Purchase" bezelStyle="rounded" alignment="center" borderStyle="border" imageScaling="proportionallyDown" inset="2" id="h9Q-rT-k8Y">
+                                    <behavior key="behavior" pushIn="YES" lightByBackground="YES" lightByGray="YES"/>
+                                    <font key="font" metaFont="system"/>
+                                </buttonCell>
+                                <connections>
+                                    <action selector="verifyPurchase:" target="XfG-lQ-9wD" id="mJm-dC-8lz"/>
+                                </connections>
+                            </button>
                         </subviews>
                         <constraints>
-                            <constraint firstAttribute="bottom" secondItem="Yzl-nj-7ol" secondAttribute="bottom" constant="22" id="979-EH-fNb"/>
+                            <constraint firstItem="NrD-IB-ZDO" firstAttribute="top" secondItem="Yzl-nj-7ol" secondAttribute="bottom" constant="12" id="76n-kS-EhS"/>
                             <constraint firstItem="Yzl-nj-7ol" firstAttribute="top" secondItem="4ix-eb-y5G" secondAttribute="bottom" constant="12" id="B88-P1-tBj"/>
                             <constraint firstAttribute="trailing" secondItem="aBh-sv-MN6" secondAttribute="trailing" id="F8t-R2-cad"/>
                             <constraint firstItem="fQC-8G-INF" firstAttribute="centerX" secondItem="m2S-Jp-Qdl" secondAttribute="centerX" id="RDD-02-SB0"/>
@@ -814,8 +824,10 @@
                             <constraint firstItem="Yzl-nj-7ol" firstAttribute="centerX" secondItem="m2S-Jp-Qdl" secondAttribute="centerX" id="dQi-Vh-Bwb"/>
                             <constraint firstItem="aBh-sv-MN6" firstAttribute="leading" secondItem="m2S-Jp-Qdl" secondAttribute="leading" id="enN-Hg-kUA"/>
                             <constraint firstItem="fQC-8G-INF" firstAttribute="top" secondItem="m2S-Jp-Qdl" secondAttribute="top" constant="20" id="kMt-Ye-T67"/>
+                            <constraint firstItem="NrD-IB-ZDO" firstAttribute="centerX" secondItem="m2S-Jp-Qdl" secondAttribute="centerX" id="qX4-iL-s2W"/>
                             <constraint firstItem="aBh-sv-MN6" firstAttribute="top" secondItem="fQC-8G-INF" secondAttribute="bottom" constant="8" id="rz5-by-FYa"/>
                             <constraint firstItem="4ix-eb-y5G" firstAttribute="centerX" secondItem="m2S-Jp-Qdl" secondAttribute="centerX" id="vs9-D1-ALb"/>
+                            <constraint firstAttribute="bottom" secondItem="NrD-IB-ZDO" secondAttribute="bottom" constant="14" id="w90-uB-Om3"/>
                         </constraints>
                     </view>
                 </viewController>

+ 47 - 10
SwiftyStoreOSXDemo/ViewController.swift

@@ -32,20 +32,21 @@ class ViewController: NSViewController {
     
     // MARK: actions
     @IBAction func getInfo1(sender: AnyObject?) {
-        getInfo("1")
+        getInfo("purchase1")
     }
-    @IBAction func getInfo2(sender: AnyObject!) {
-        getInfo("2")
+    @IBAction func getInfo2(sender: AnyObject?) {
+        getInfo("consumablePurchase")
     }
-    @IBAction func purchase1(sender: AnyObject!) {
-        purchase("1")
+    @IBAction func purchase1(sender: AnyObject?) {
+        purchase("purchase1")
     }
-    @IBAction func purchase2(sender: AnyObject!) {
-        purchase("2")
+    @IBAction func purchase2(sender: AnyObject?) {
+        purchase("consumablePurchase")
     }
+
     func getInfo(no: String) {
 
-        SwiftyStoreKit.retrieveProductsInfo([AppBundleId + ".purchase" + no]) { result in
+        SwiftyStoreKit.retrieveProductsInfo([AppBundleId + "." + no]) { result in
 
             self.showAlert(self.alertForProductRetrievalInfo(result))
         }
@@ -53,7 +54,7 @@ class ViewController: NSViewController {
 
     func purchase(no: String) {
 
-        SwiftyStoreKit.purchaseProduct(AppBundleId + ".purchase" + no) { result in
+        SwiftyStoreKit.purchaseProduct(AppBundleId + "." + no) { result in
 
             self.showAlert(self.alertForPurchaseResult(result))
         }
@@ -67,7 +68,7 @@ class ViewController: NSViewController {
         }
     }
 
-    @IBAction func verifyReceipt(ender: AnyObject?) {
+    @IBAction func verifyReceipt(sender: AnyObject?) {
 
         SwiftyStoreKit.verifyReceipt() { result in
 
@@ -78,6 +79,27 @@ class ViewController: NSViewController {
         }
     }
 
+    @IBAction func verifyPurchase(sender: AnyObject?) {
+        
+        SwiftyStoreKit.verifyReceipt() { result in
+            
+            switch result {
+            case .Success(let receipt):
+                
+                let purchaseResult = SwiftyStoreKit.verifyPurchase(
+                    productId: self.AppBundleId + "consumablePurchase",
+                    inReceipt: receipt,
+                    validUntil: NSDate()
+                )
+                self.showAlert(self.alertForVerifyPurchase(purchaseResult))
+                
+            case .Error(_):
+                self.showAlert(self.alertForVerifyReceipt(result))
+            }
+        }
+    }
+    
+
 
 }
 
@@ -171,5 +193,20 @@ extension ViewController {
         }
     }
 
+    func alertForVerifyPurchase(result: SwiftyStoreKit.VerifyPurchaseResult) -> NSAlert {
+        
+        switch result {
+        case .Purchased(let expiresDate):
+            if let expiresDate = expiresDate {
+                return alertWithTitle("Product is purchased", message: "Product is valid until \(expiresDate)")
+            }
+            return alertWithTitle("Product is purchased", message: "Product will not expire")
+        case .Expired(let expiresDate): // Only for Automatically Renewable Subscription
+            return alertWithTitle("Product expired", message: "Product is expired since \(expiresDate)")
+        case .NotPurchased:
+            return alertWithTitle("Not purchased", message: "This product has never been purchased")
+        }
+    }
+
 }