<?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0" xmlns:cc="http://cyber.law.harvard.edu/rss/creativeCommonsRssModule.html">
    <channel>
        <title><![CDATA[Stories by Gianpiero Spinelli on Medium]]></title>
        <description><![CDATA[Stories by Gianpiero Spinelli on Medium]]></description>
        <link>https://medium.com/@gianpispi?source=rss-d6528145285f------2</link>
        <image>
            <url>https://cdn-images-1.medium.com/fit/c/150/150/1*Tr9pXfRw-iKmuYCwwDpo6Q.jpeg</url>
            <title>Stories by Gianpiero Spinelli on Medium</title>
            <link>https://medium.com/@gianpispi?source=rss-d6528145285f------2</link>
        </image>
        <generator>Medium</generator>
        <lastBuildDate>Sat, 14 Nov 2026 17:33:06 GMT</lastBuildDate>
        <atom:link href="https://medium.com/@gianpispi/feed" rel="self" type="application/rss+xml"/>
        <webMaster><![CDATA[yourfriends@medium.com]]></webMaster>
        <atom:link href="http://medium.superfeedr.com/" rel="hub"/>
        <item>
            <title><![CDATA[How to use xcassets for alternative icons]]></title>
            <link>https://medium.com/@gianpispi/how-to-use-xcassets-for-alternative-icons-20849f836e2f?source=rss-d6528145285f------2</link>
            <guid isPermaLink="false">https://medium.com/p/20849f836e2f</guid>
            <category><![CDATA[apple]]></category>
            <category><![CDATA[apps]]></category>
            <category><![CDATA[swift]]></category>
            <category><![CDATA[ios]]></category>
            <category><![CDATA[app-icon]]></category>
            <dc:creator><![CDATA[Gianpiero Spinelli]]></dc:creator>
            <pubDate>Mon, 29 Nov 2021 23:01:26 GMT</pubDate>
            <atom:updated>2021-11-29T23:18:25.444Z</atom:updated>
            <content:encoded><![CDATA[<h4>Without loosing your mind.</h4><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*XmT3vhp--wXTh3KtTw7nGg.png" /></figure><p>Perhaps you heard about the possibility to use xcassets for alternative icons in Xcode 13. I did as well. I then opened Xcode 13, created a new App Icon Set to tried that. Hit Run and… <em>“The file doesn’t exist”</em>. I tried to debug the problem in many ways, by printing variables’ content and by using breakpoints. I also tried to add the icons to the Info.plist file, as our ancestors (us until last June) used to do. None of this would do; the error was still there.</p><p>I tried to search the problem on the internet. Radio silence. No one has ever had that issue. Apple hasn’t publish anything on this topic ever. No sessions from WWDC, nor documentation (or at least not that I found).</p><p>After a few hours of banging my head on the keyboard, I stumbled upon the <a href="https://developer.apple.com/documentation/xcode-release-notes/xcode-13-release-notes">release notes of Xcode 13</a>, and found the Holy Graal:</p><blockquote><em>At runtime, your app can now use iOS app icon assets from its asset catalog as alternate app icons. A new build setting, “Include all app icon assets,” controls whether Xcode includes all app icon sets in the built product. When the setting is disabled, Xcode includes the primary app icon, along with the icons specified in the new setting, “Alternate app icon sets.” The asset catalog compiler inserts the appropriate content into the </em><em>Info.plist of the built product. (33600923)</em></blockquote><p>Basically you just need to set to <strong>YES</strong> the “Include All App Icon Assets” setting under <strong>build settings</strong>.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*mmw6dsGRRZTerejDkTC_6g.png" /></figure><p>Once you do that you can finally use the App Icon Sets in your xcasset catalog as alternate app icons as you usually do.</p><p>There is another way. Instead of setting to true “<strong>Include All App Icon Assets</strong>”, you can select which App Icon Assets to use. Just insert the names of the icons sets you want to use under the “<strong>Alternate App Icon Sets</strong>“. In the example below we are only including the icon set called &quot;chaos&quot;.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*6nEJYUlzCmL3gzFUgy7ReA.png" /></figure><p>Let’s refresh how to implement alternate icons in code. First of all we need at least an app icon bundle in the xcasset catalog. Something like in the image below.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*wieQKbbfNqIBeTQN7dpBZg.png" /></figure><p>Once we have the asset ready, we can set the icon. Let’s switch to the code.</p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/73f891fa8af283d5e8705153fd680b58/href">https://medium.com/media/73f891fa8af283d5e8705153fd680b58/href</a></iframe><p>Here we are creating an @IBAction function, that sets the alternate icon named &quot;chaos&quot;, that we previously selected in the build settings.</p><p>We are done. This is enough to change the app icon to a precise icon. If you want to go back to the default icon, just put nil instead of &quot;chaos&quot; in the parameter of the setAlternateIconName function.</p><p>I made a demo app in SwiftUI, with a table view and some funny icons. You can find it <a href="https://github.com/gianpispi/icony">here</a>.</p><img src="https://medium.com/_/stat?event=post.clientViewed&referrerSource=full_rss&postId=20849f836e2f" width="1" height="1" alt="">]]></content:encoded>
        </item>
        <item>
            <title><![CDATA[How to Programmatically Create a Preference-Styled Toolbar in macOS Catalyst]]></title>
            <link>https://medium.com/better-programming/how-to-programmatically-create-a-preference-styled-toolbar-in-macos-catalyst-d7c370199c49?source=rss-d6528145285f------2</link>
            <guid isPermaLink="false">https://medium.com/p/d7c370199c49</guid>
            <category><![CDATA[programming]]></category>
            <category><![CDATA[macos]]></category>
            <category><![CDATA[swift]]></category>
            <category><![CDATA[big-sur]]></category>
            <category><![CDATA[catalyst]]></category>
            <dc:creator><![CDATA[Gianpiero Spinelli]]></dc:creator>
            <pubDate>Mon, 30 Nov 2020 16:25:46 GMT</pubDate>
            <atom:updated>2020-11-30T16:25:46.388Z</atom:updated>
            <content:encoded><![CDATA[<h4>Better toolbar styling in Catalyst</h4><figure><img alt="Preference-styled toolbar" src="https://cdn-images-1.medium.com/max/1024/1*YvJEzaoQkdDrMVOklK9mQw.png" /><figcaption>Photo by the author.</figcaption></figure><p>Big Sur brings a massive redesign to the Mac. It offers new icons and a new, cleaner UI design while keeping the character of macOS. It also gives us great improvements for Catalyst development, but today we are going to talk about the new Preference style for the toolbar.</p><p>Our aim for this article is to create a preference controller with this toolbar style. This style already existed before, but Big Sur takes a different approach to it. It now has a cleaner look and feel, and it is used in more and more applications. This tutorial assumes that you already have a Scene for the preferences window.</p><h3>Let’s Start Coding</h3><p>First off, we need to add a toolbar in our window. In our SettingsViewController, we make a new function called insertToolbar():</p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/97a47779b8b152f28c9da0ce5b354116/href">https://medium.com/media/97a47779b8b152f28c9da0ce5b354116/href</a></iframe><p>Let’s break down the code we just wrote:</p><ol><li>We check if we are building for Mac or iOS.</li><li>We create a scene object from the current windowScene if it exists. If it does not exist, the function returns.</li><li>We check if there is a titlebar in the scene.</li><li>We create a toolBar object of type NSToolbar with the mainToolbar identifier. We are also assigning ToolbarIdentifers.general to the selectedItemIdentifier property of the toolBar. This will give you an error now that will be fixed later on.</li><li>We set the toolBar style to .preferece, to give it the look we want;</li><li>We assign the toolBar object we just created to the toolbar property of our titleBar.</li></ol><p>We assign self, our controller, to the toolBar&#39;s delegate. It returns an error right now because our controller does not conform to the NSToolbarDelegate yet. In order to address this, we create an extension of the ViewController like this:</p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/f1511c9d90488836de07970e2ea7b29a/href">https://medium.com/media/f1511c9d90488836de07970e2ea7b29a/href</a></iframe><p>In this new extension, we are going to implement some toolbar functions. First, it is good practice to create some identifier constants instead of writing a string every time we need to address one specific identifier. This will reduce the risk of misspelling anything. So in the extension we just created, we put this enum:</p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/718eee31f415a198144c2b54fbb684e6/href">https://medium.com/media/718eee31f415a198144c2b54fbb684e6/href</a></iframe><p><em>Note: For simplicity’s sake, I am going to hard-code the SF Symbols’ names later.</em></p><h3>Digression for Identifiers</h3><p>In order to have all the constants in one place, you can create an enum this way:</p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/da723448b85f34c5f55dba64ac907bca/href">https://medium.com/media/da723448b85f34c5f55dba64ac907bca/href</a></iframe><h3>Back to the Real Coding</h3><p>We just created the identifiers of our items. Now we have to tell the toolbar what to display and how. We start by adding the public func toolbarAllowedItemIdentifiers(_ toolbar: NSToolbar) -&gt; [NSToolbarItem.Identifier] method that tells the toolbar which items are allowed in it:</p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/c6cc71472933c06c6507f2201c6da65e/href">https://medium.com/media/c6cc71472933c06c6507f2201c6da65e/href</a></iframe><p>It has to return an array of NSToolbarItem.Identifier, which consists of the identifiers we set a few steps ahead. Now we need to tell our toolbar which are the default items and which of them are selectable in order for them to get the behaviour we expect:</p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/7e9c9257acf80ba02590c8954d17097f/href">https://medium.com/media/7e9c9257acf80ba02590c8954d17097f/href</a></iframe><p>We are one method away from the end. We need to determine how the button should look and what it has to do when pressed. public func toolbar(_ toolbar: NSToolbar, itemForItemIdentifier itemIdentifier: NSToolbarItem.Identifier, willBeInsertedIntoToolbar flag: Bool) -&gt; NSToolbarItem? comes to the rescue:</p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/9e2650113513b647517844a4d99ecc16/href">https://medium.com/media/9e2650113513b647517844a4d99ecc16/href</a></iframe><p>In this method, we are telling our toolbar which items belong to which identifier. The three methods at the bottom are the actions our items perform. Change the content of the controller there.</p><h3>Build and Run</h3><p>Let’s build and run our app. Congratulations, you did it! Here is the result of this work:</p><figure><img alt="Final toolbar" src="https://cdn-images-1.medium.com/max/1024/0*Bz6hvoq5JGUB68ic" /></figure><h3><strong>Bonus</strong></h3><p>In order to change the title of the window when you change the tab, we have to change the scene title, which can be done this way:</p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/572656c41cfcc266f4379f9a657756e6/href">https://medium.com/media/572656c41cfcc266f4379f9a657756e6/href</a></iframe><p>The code used in this article can be found on <a href="https://github.com/gianpispi/">GitHub</a>.</p><img src="https://medium.com/_/stat?event=post.clientViewed&referrerSource=full_rss&postId=d7c370199c49" width="1" height="1" alt=""><hr><p><a href="https://medium.com/better-programming/how-to-programmatically-create-a-preference-styled-toolbar-in-macos-catalyst-d7c370199c49">How to Programmatically Create a Preference-Styled Toolbar in macOS Catalyst</a> was originally published in <a href="https://betterprogramming.pub/">Better Programming</a> on Medium, where people are continuing the conversation by highlighting and responding to this story.</p>]]></content:encoded>
        </item>
        <item>
            <title><![CDATA[How To Share a Photo on Instagram Stories in Swift]]></title>
            <link>https://medium.com/better-programming/how-to-share-a-photo-on-instagram-stories-in-swift-75319a669596?source=rss-d6528145285f------2</link>
            <guid isPermaLink="false">https://medium.com/p/75319a669596</guid>
            <category><![CDATA[ios]]></category>
            <category><![CDATA[programming]]></category>
            <category><![CDATA[instagram]]></category>
            <category><![CDATA[mobile]]></category>
            <category><![CDATA[swift]]></category>
            <dc:creator><![CDATA[Gianpiero Spinelli]]></dc:creator>
            <pubDate>Thu, 06 Feb 2020 14:57:21 GMT</pubDate>
            <atom:updated>2020-02-07T20:23:15.727Z</atom:updated>
            <content:encoded><![CDATA[<h4>Share a custom photo or video to Instagram Stories via its rich URL scheme</h4><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*0TyN8Uwe3oKEHHyOYnOYmw.jpeg" /></figure><p>Instagram implements a rich URL scheme for its Stories. The best thing about URL schemes is that we don’t need to include any frameworks. If the user has the Instagram app installed, it will do all the dirty work. Let’s dive into more details!</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*ggUpi-Hy_NBpViP-eGtfyA.png" /><figcaption>Photo on the third screen from <a href="https://unsplash.com/">Unsplash</a>.</figcaption></figure><p>As you can see in the image above, there are three main layers:</p><ul><li>The background layer, which can be made of a photo, a video, a solid color, or a gradient.</li><li>The sticker layer (optional), which contains an image and can be edited by the user.</li><li>The attribution link (in beta for some users only).</li></ul><h3>Time to Code</h3><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/e05513a324e27e47306f8c17a546ea6d/href">https://medium.com/media/e05513a324e27e47306f8c17a546ea6d/href</a></iframe><p>Let’s review the code.</p><ol><li>Basically, here we created a URL with Instagram’s scheme. We are using the optional binding if-let because the URL init returns an optional value.</li><li>After that, we checked if the system can open Instagram — or rather if it is on the device.</li><li>Once we are sure of that, we can proceed. In order to pass an image or a video, we have to convert it into data. For images, we can use .pngData()<em>.</em> Once we convert our image or video to the correct format, we need to copy that in the system pasteboard, where Instagram will get the data from.</li><li>We now create an array of dictionaries the type we need to put something in the pasteboard. We also create the options for the pasteboard, and in this case, we set the expiration date for our image. That will be five minutes.</li><li>This step is important since we set the items (our image data) to the pasteboard with our options (five minutes of life).</li><li>Finally, we open the URL we created at the beginning. Instagram will open and it will show our image in the story composer.</li></ol><p>We did it!</p><h3>More Customization</h3><p>But what about using a video, gradient, or sticker as the background?</p><h4>Background image/video</h4><p>As said above, in order to have a background image or video, we need to set a data<strong> </strong>object for one of these two keys:</p><pre>com.instagram.sharedSticker.backgroundImage</pre><pre>com.instagram.sharedSticker.backgroundVideo</pre><h4>Sticker</h4><p>As an image, a sticker also accepts data. The recommended size is 640x480px. The key for the sticker is:</p><pre>com.instagram.sharedSticker.stickerImage</pre><h4>Gradient background</h4><p>For a gradient background, we need to pass two colors: one for the top and one for the bottom. In this case, we have to pass a string with the HEX value of the color.</p><pre>com.instagram.sharedSticker.backgroundTopColor<br>com.instagram.sharedSticker.backgroundBottomColor</pre><p>For example:</p><pre><strong>let</strong> items = [[&quot;com.instagram.sharedSticker.backgroundTopColor&quot;: &quot;#EA2F3F&quot;, &quot;com.instagram.sharedSticker.backgroundBottomColor&quot;: &quot;#8845B9&quot;]]</pre><p>To get a solid background, we do the same thing as with a gradient, but the two colors have to match.</p><img src="https://medium.com/_/stat?event=post.clientViewed&referrerSource=full_rss&postId=75319a669596" width="1" height="1" alt=""><hr><p><a href="https://medium.com/better-programming/how-to-share-a-photo-on-instagram-stories-in-swift-75319a669596">How To Share a Photo on Instagram Stories in Swift</a> was originally published in <a href="https://betterprogramming.pub/">Better Programming</a> on Medium, where people are continuing the conversation by highlighting and responding to this story.</p>]]></content:encoded>
        </item>
        <item>
            <title><![CDATA[How To Create a Framework With Carthage Support]]></title>
            <link>https://medium.com/better-programming/how-to-create-a-framework-with-carthage-support-c30b596d3a7a?source=rss-d6528145285f------2</link>
            <guid isPermaLink="false">https://medium.com/p/c30b596d3a7a</guid>
            <category><![CDATA[framework]]></category>
            <category><![CDATA[swift]]></category>
            <category><![CDATA[carthage]]></category>
            <category><![CDATA[ios]]></category>
            <category><![CDATA[apple]]></category>
            <dc:creator><![CDATA[Gianpiero Spinelli]]></dc:creator>
            <pubDate>Fri, 09 Aug 2019 11:40:24 GMT</pubDate>
            <atom:updated>2020-03-03T15:41:30.240Z</atom:updated>
            <content:encoded><![CDATA[<h3>How To Create A Framework With Carthage Support</h3><h4>Frameworks management simplified</h4><figure><img alt="" src="https://cdn-images-1.medium.com/max/860/1*Xv_W2QYW2zTO0pYSEIpX3w.jpeg" /></figure><p>Perhaps you’re wondering what Carthage is. Carthage is a decentralized dependency manager for cocoa. What does that mean? It means that it simplifies our lives by taking care of all the problems that depend on frameworks management.</p><p>At the end of this guide, you will have a basic framework supported by <a href="https://github.com/Carthage/Carthage">Carthage</a>.</p><h3>Action!</h3><p>To proceed, you need some packages on your computer. I recommend installing <a href="https://brew.sh/index_it">Homebrew</a>, a packet manager that simplifies your life with installations.</p><p>If you do not have Carthage already installed already, run this command:</p><p>brew install carthage</p><p>Once you have done that, <em>you’re ready to start!</em></p><h3>Create the Framework</h3><p>First, we have to create our framework. In this case, we’re going to make a simple method to change the view’s background color. Create a new Xcode project, <em>iOS, Cocoa Touch Framework:</em></p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*8hGRqcRfAEqoiypT3QNu5Q.png" /></figure><p>Click next and then give it a name (I’ll call it <em>GSKit</em>).</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*aj_ysfW57dubVmWakDvwcw.png" /></figure><p>Click on next once more and save.</p><h3>Add Git Control</h3><p>In order to share your framework you have to put it on Github, so let’s create the local git versioning. Open Terminal, cd the project&#39;s folder and the execute git init. It creates a local version of git that we’ll upload later.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*m_YhQrqr46kis1Cr7GXQPg.png" /></figure><h3>Start Coding</h3><p>Now we need something to execute. So let’s create a file: Cmd+N, select Swift File, name it <em>GSViewController</em> and save it. Now let’s write some code:</p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/6e559f0a79cb560d6233d96c5a931a05/href">https://medium.com/media/6e559f0a79cb560d6233d96c5a931a05/href</a></iframe><p>You should have something that looks like this:</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*MGykEu1DCGKBIurASPDgUw.png" /></figure><p>Let’s review the code we just wrote:</p><ul><li><em>Line 9</em>: we’re importing the UIKit framework in order to be able to use the references to UIViewController and to UIColor.</li><li><em>Line 11</em>: we’re creating a new class called <em>GSViewController</em> that inherits the <em>UIViewController</em> class. We put the class <em>open </em>in order to be able to inherit it outside its target.</li><li><em>Line 12</em>: we created a function called changeBackground with a parameter called ::color:: of type UIColor. The function is public because we want to use it outside this framework. In the function we are simply changing the color of the background.</li></ul><h3>Sample Project</h3><p>We are going to create a sample application to showcase how to use our beautiful new framework. To create this app, click on the project and then click on the plus icon on the bottom left.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*k7sFar9XjzEsOzfxCNhTZg.png" /></figure><p>Then select iOS, and Single View App. Name it Example and save it.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*_TmN3jNZ2sw9HS4f1MqLRw.png" /></figure><p>Next, we have to link the framework in order to be able to use it in our Example application. Click on the plus icon under Linked Frameworks and Libraries and select GSKit from the menu.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*cgqZ6eHf2QrorVO77rMcew.png" /></figure><h3>Test our Framework</h3><p>Now we can test if the framework works in the right way by using this code in the ViewController class.</p><pre>import UIKit<br>import GSKit<br><br>class ViewController: GSViewController {<br>    <br>    var colors: [UIColor] = [.red, .green, .blue, .orange, .purple]<br>    var currentIndex = 0<br>    <br>    override func viewDidLoad() {<br>        super.viewDidLoad()<br>        <br>        changeBackground(withColor: colors[currentIndex])<br>        <br>        self.view.addGestureRecognizer(UITapGestureRecognizer(target: self, action: #selector(handleClick)))<br>    }<br>    <br>    @objc func handleClick() {<br>        currentIndex += 1<br>        <br>        if !colors.indices.contains(currentIndex) {<br>            currentIndex = 0<br>        }<br>        <br>        changeBackground(withColor: colors[currentIndex])<br>    }<br>}</pre><figure><img alt="" src="https://cdn-images-1.medium.com/max/591/1*-19ZdHFvAxD1XIGEU2L3SA.png" /></figure><p>Change the build target to Example and run the app. It will open an app with a red background — if you click on the view the color changes. It works!</p><p>Click on Manage Schemes, and then un-flag and re-flag the “Shared” voice near GSKit.</p><h3>Build for Carthage</h3><p>Now it’s time to build our framework in Carthage. If you closed the Terminal window, reopen it and navigate again to the project’s folder. The only thing we need to do now is run this command: carthage build --no-skip-current. It will build the framework and create a <em>Carthage</em> folder in the project folder.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*XTJP2hzt6v44aTd389Qulw.png" /></figure><p>We’re one step from the end! All we need to do now is push the folder to GitHub. To do that we use this command in Terminal:</p><pre>add .<br>git commit -m &#39;first commit&#39;<br>git tag &quot;v1.0&quot;<br>git remote add origin &quot;URL OF THE REPO&quot;<br>git push origin &quot;v1.0&quot;</pre><p>You need to first create a repo on GitHub. URL OF THE REPO is the link to the repo you created.</p><p><em>The framework has now been published on GitHub!</em></p><h3>How To Use It</h3><p>To use it, all you need to do is create a <a href="https://github.com/Carthage/Carthage/blob/master/Documentation/Artifacts.md#cartfile">Cartfile</a> and add this: git &quot;URL OF THE REPO&quot; ~&gt; 1.0</p><p>Save the file, open the Terminal, navigate to the project’s folder and run carthage update.</p><p>Drag the framework from Carthage/Build/iOS/GSKit.framework to the Linked Frameworks and Libraries in the target in Xcode.</p><p>Now you have to create a New Run Script Phase for the application target’s Build Phases with:/usr/local/bin/carthage copy-frameworks</p><p>In the Input Files you have to add this:$(SRCROOT)/Carthage/Build/iOS/GSKit.framework</p><p>And this in the Output Files:$(BUILT_PRODUCTS_DIR)/$(FRAMEWORKS_FOLDER_PATH)/GSKit.framework</p><p>All done! You can now use your framework in your new project!</p><p>You can find the code from this project in <a href="https://github.com/gianpispi/GSKit">my repo on GitHub</a>.</p><img src="https://medium.com/_/stat?event=post.clientViewed&referrerSource=full_rss&postId=c30b596d3a7a" width="1" height="1" alt=""><hr><p><a href="https://medium.com/better-programming/how-to-create-a-framework-with-carthage-support-c30b596d3a7a">How To Create a Framework With Carthage Support</a> was originally published in <a href="https://betterprogramming.pub/">Better Programming</a> on Medium, where people are continuing the conversation by highlighting and responding to this story.</p>]]></content:encoded>
        </item>
        <item>
            <title><![CDATA[How to deploy a Swift backend on Amazon AWS]]></title>
            <link>https://medium.com/@gianpispi/how-to-deploy-a-swift-backend-on-amazon-aws-ea9213518c43?source=rss-d6528145285f------2</link>
            <guid isPermaLink="false">https://medium.com/p/ea9213518c43</guid>
            <category><![CDATA[ios]]></category>
            <category><![CDATA[ios-app-development]]></category>
            <category><![CDATA[mobile-app-development]]></category>
            <category><![CDATA[mobile]]></category>
            <category><![CDATA[swift]]></category>
            <dc:creator><![CDATA[Gianpiero Spinelli]]></dc:creator>
            <pubDate>Thu, 04 Apr 2019 10:35:17 GMT</pubDate>
            <atom:updated>2020-02-05T17:20:41.064Z</atom:updated>
            <content:encoded><![CDATA[<figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*Y9BXxnGp1ZNjLeqhQ9NrnQ.jpeg" /></figure><p>Have you ever heard the word “<strong>backend</strong>”? If this is your first time hearing this strange word and you are wondering if it is an animal or a particular kind of plant or even a really tasty food, or if you know what that is but you feel like you don’t really know much about it, <strong>follow me</strong> during this guide, and in the end you will be quite an expert about it.</p><p>At the end of this guide, you will have a basic backend for your application. To reach this goal, we are going to use <a href="https://www.kitura.io/">Kitura</a>, a server-side web framework that allows us to build a server using <a href="https://swift.org/">Swift</a>, for API’s endpoints, <a href="https://www.postgresql.org/">Postgres</a>, an open source relational database, for storing data and <a href="https://www.docker.com/">Docker</a> to manage the resources.</p><figure><img alt="" src="https://cdn-images-1.medium.com/proxy/1*q5g4vlCvfm8J-m38ieL36g.jpeg" /></figure><p>Probably now you are WAT?! What is an API Endpoint? I’ll help you!</p><blockquote>An API is a programmatic interface consisting of one or more publicly exposed endpoints to a defined request–response message system, typically expressed in JSON, which is exposed through HTTPS protocol.</blockquote><p>In this guide, we are going to use HTTP instead of HTTPS, because, in order to support the apparently irrelevant letter, in the end, there are a lot of hard and long steps.</p><p>At the end, we will have three API endpoints. We will be able to query these endpoints getting a JSON response. The database is a database made by three tables, that describe the structure for a travelling app.</p><h4>Action!</h4><p>Here we are. First of all, there are some prerequisites needed. For Kitura, if you are using macOS, you need to install <a href="https://itunes.apple.com/it/app/xcode/id497799835?l=en&amp;mt=12">Xcode 9 or later</a>, and run xcode-select --install on the Terminal. If you are using Linux, follow <a href="https://www.kitura.io/guides/building/settingup.html">this guide</a>.</p><p>To proceed, you are going to need some other packages on your computer. I recommend installing <a href="https://brew.sh/index_it">Homebrew</a>, a packet manager that simplifies your life with used-to-be-messy installations.</p><p>Now that everything is set up, install Kitura through Homebew:</p><pre>$ brew tap ibm-swift/kitura<br>$ brew install kitura</pre><p>Now it’s time to install Docker, a powerful tool that helps you managing scalable backends, and deploy it with ease. Download <a href="https://hub.docker.com/editions/community/docker-ce-desktop-mac">Docker</a> and install it following the in-app steps. Take your time, and once it’s installed, login in and come back here.</p><p>You just installed everything you need, congratulation! Now we need a <em>project folder.</em> Our hierarchy is composed of a main folder called “MyFirstBackend”. In it, we are going to create two other folders: “<em>backend</em>”, “<em>certificates</em>” and “<em>database</em>”.We will use these folders to store the rules for the images of the docker containers. Later, in the database folder, we will put the rules to create the… guess it: database. In the backend folder, instead, we will instantiate the Kitura project. Seems fun, right? Let’s dig into it!</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*ki_Qh5tFWJ9FylhYd5aH1w.png" /></figure><h4>Postgres, it’s your turn!</h4><p>Docker, as said before, is a really powerful program that performs operating-system virtualizations. We are using it because we will deploy our backend on the cloud. In this way, you will not care about memory, space and all the limitations of a normal web hosting. This is possible thanks to the cloud and the scalability of it.</p><p>Let’s build the database now! In the “<em>database</em>” folder we are going to give the rules for the Postgres database. Go back to the Terminal, and cd the <em>database</em> folder. In there create the Dockerfile and a SQL file</p><pre>$ cd path/to/database/<br>$ touch Dockerfile<br>$ touch CreateDB.sql</pre><p>Two files have been created in the <em>database</em> folder. One is the Dockerfile, a file with all the instruction for the creation of the Docker image, and the other one is a supporting file that we need to create the actual database structure. Let’s open the Dockerfile. Now that you have an empty text file in front of you, let’s write some instructions for the Docker container.</p><pre>FROM postgres:latest</pre><pre>ENV POSTGRES_USER root<br>ENV POSTGRES_PASSWORD admin<br>ENV POSTGRES_DB myFirstDatabase</pre><pre>ADD CreateDB.sql /docker-entrypoint-initdb.d/</pre><p>When we will build these rules, Docker will download the latest Postgres image from DockerHub, will create a user for the database with <em>root</em> as username and <em>admin</em> as password. The name of the database will be <em>myFirstDatabase</em>. Everything will be based on the <em>CreateDB.sql</em> file we created a minute ago.</p><p>Now it’s time to create the database structure.</p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/2c9dff9cf87899324addbb0bf963a0b3/href">https://medium.com/media/2c9dff9cf87899324addbb0bf963a0b3/href</a></iframe><p>This is the structure we are going to use. There are three tables: users, places and trips.</p><p>With the first command, we create the <em>users</em> table, which has:</p><ul><li>user_id: the autoincremetal (SERIAL) primary key</li><li>username, email, password: the text properties for each tuple of <em>users</em></li><li>username, email: these properties are marked UNIQUE, which means that will not be possible to insert a value that already exists</li></ul><p>Then we populate the users table with a bunch of values. We have made the same process to create the <em>places</em> table. After this, we have created the third table called <em>trip</em> which is a relationship between the previous two tables. In this table, we have 2 fields that are depending on the other tables, and we do this with the FOREIGN KEY () REFERENCE () syntax.</p><h4>Kitura, I choose you!</h4><p>Just move in the backend folder and use Kitura to generate a ready to build OpenAPI project on the spot:</p><pre>$ cd path/to/backend/<br>$ kitura init</pre><p>Now open the generated Xcode project. To communicate with the database, we need to import some frameworks. In the <em>Package</em> file, import these two IBM’s frameworks and update the dependencies. The first one stands for “Object Relational Mapping” and it will facilitate us with the queries to our database. The second one is needed since we use PostgreSQL. Be aware that for advanced custom queries you would opt for using directly Swift-Kuery rather than Swift-Kuery-ORM.</p><pre>.package(url: &quot;https://github.com/IBM-Swift/Swift-Kuery-ORM.git&quot;, from: &quot;0.4.1&quot;),<br>.package(url: &quot;https://github.com/IBM-Swift/Swift-Kuery-PostgreSQL.git&quot;, from: &quot;2.1.0&quot;)</pre><pre>.target(name: &quot;Application&quot;, dependencies: [&quot;SwiftKueryPostgreSQL&quot;, &quot;SwiftKueryORM&quot;, ...</pre><p>You have to regenerate the project for the new dependencies. First, close Xcode and use these commands:</p><pre>$ cd backend/<br>$ swift package generate-xcodeproj</pre><p>Reopen the project, you can now import them within the Application.swift file:</p><pre>import SwiftKueryORM<br>import SwiftKueryPostgreSQL</pre><p>Now let’s prepare our model to relate to the database. We need it to conform to Codable, Equatable and Model protocols:</p><ul><li><strong>Codable</strong>: it allows the struct to be exported in JSON</li><li><strong>Equatable</strong>: it allows to compare for equality different User objects</li><li><strong>Model</strong>: this exposes new methods for saving, finding, deleting etc. from a database</li></ul><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/e46473d350c98ec0b2cbb79949a36205/href">https://medium.com/media/e46473d350c98ec0b2cbb79949a36205/href</a></iframe><p>Now we have to establish the connection to the database. Insert this function within the App class in Application.swift:</p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/613995ca6e9e07bade89aa98806ca82e/href">https://medium.com/media/613995ca6e9e07bade89aa98806ca82e/href</a></iframe><p>Just change the parameters accordingly with your databaseName, userName and password.</p><p>Now let’s support GET requests in two variants within the App class:</p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/111ab0ad28425e9b904cd06067ecf0df/href">https://medium.com/media/111ab0ad28425e9b904cd06067ecf0df/href</a></iframe><p>Hey, you are ready to go!</p><h4>Docker: how to!</h4><p>At this point you should have a structure like this:</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*tXwhMSZAXh7A-IFfDXmXHA.png" /></figure><p>Now we have all the Dockerfiles we need. Some lines above we created the Dockerfile for our database, and then we instantiated a Kitura project, that creates a Dockerfile automatically. This Dockerfile misses a variable. Open the file you can find in the backend folder, remove everything and write:</p><pre>FROM ibmcom/kitura-ubuntu:latest<br>RUN mkdir /external &amp;&amp; apt-get update &amp;&amp; apt-get -y upgrade &amp;&amp; apt-get -y install curl<br>RUN curl -sL <a href="https://deb.nodesource.com/setup_10.x">https://deb.nodesource.com/setup_10.x</a> | sudo -E bash -<br>RUN apt-get update &amp;&amp; apt-get -y upgrade &amp;&amp; apt-get install -y nodejs libpq-dev<br>RUN npm install -g yo<br>EXPOSE 8080<br>ENV DATABASE_URL 127.0.0.1<br>ADD ./ /external/<br>RUN [&quot;/bin/bash&quot;, &quot;-c&quot;, &quot;cd /external/; swift build&quot;]<br>CMD [&quot;/bin/bash&quot;, &quot;-c&quot;, &quot;cd /external/.build/x86_64-unknown-linux/debug/; ./backend&quot;]</pre><p>Now we just have to build the docker images. In order to achieve that, we need to run some commands. First of all, run docker opening the app, we installed at the beginning. When it is running, go back to Terminal and change directories to the main project’s folder (myFirstBackend). To finally build the images, you need to run these commands:</p><pre>docker build -t username/mydatabase:v1 ./database<br>docker build -t username/mybackend:v1 ./backend</pre><p>Where:</p><ul><li><strong>username</strong>: the username of your DockerHub account</li><li><strong>mydatabase — mybackend</strong>: name of the images</li><li><strong>v1</strong>: tag of the version you are building</li></ul><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*WgMhIMpf9_fvn_GT_o--Qg.png" /></figure><p>You can test your images by running them on your machine. The database needs to run on port 5432:</p><pre>docker run -p 5432:5432 username/mydatabase:v1</pre><p>When the database is running, run the backend on port 8080, and change the environment variable with your local IP. To find your local IP, open System Preferences, then go to Network, and look at your current IP address. Set that address as DATABASE_URL:</p><pre>docker run -p 8080:8080 -e DATABASE_URL=&#39;&#39; username/mybackend:v1</pre><p>When this step is done, you need to upload these images on DockerHub with:</p><pre>docker push username/mydatabase:v1<br>docker push username/mybackend:v1</pre><blockquote>Remember to replace the username with your DockerHub username.</blockquote><h4>Deploy everything</h4><p>We are almost done! Now it is the moment to deploy what you have done so far, on the cloud, that in this case is <a href="https://aws.amazon.com/">Amazon AWS</a>. First of all, you need an account there. If you don’t have one, create it <a href="https://portal.aws.amazon.com/billing/signup?nc2=h_ct&amp;src=header_signup&amp;redirect_url=https%3A%2F%2Faws.amazon.com%2Fregistration-confirmation#/start">here</a>. Once you have one, login, and, under <strong>services</strong>, select <strong>EC2</strong>. On the top right, you can select the region of the server you want to work on. In this tutorial, we are using <strong>US. West (N. California)</strong> but you can decide the one which better suits your needs.</p><p>To run your docker images on AWS you need an instance. To create one, select <em>Instances</em> in the menu on the left and a select the “Launch Instance” blue button in the middle of the page.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*9DydXueVhybEe8ErXlrjUg.png" /></figure><p>Now it is time to configure your machine. Choose <strong>Amazon Linux 2 AMI</strong> by clicking the <em>Select</em> button.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*1mEl-XiU10EDIsU7P4lvfA.png" /></figure><p>Technical specifications are important for your instance since they determine the limit of your app.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*EMLkptTdURwQw_K87YHo_A.png" /></figure><p>Configure the security group and stay away from bad and unexpected scenarios. Open just the ports you need to run your backend. The HTTP is the protocol you will use to load the API, so the source is set to <strong>everywhere</strong> so the service will be accessible from everywhere.</p><blockquote>Note: For testing purposes, we are setting SSH sources to anywhere, but for a better security, the SSH port should be opened just for your IP Address. In this way, no one can access your instance via SSH.</blockquote><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*bJqE2i4hXF42ohsI4C8RBg.png" /></figure><p>Once you reviewed all the details, click <em>Launch</em>. In this way, you will deploy the instance and you will be able to create a pair of keys you will need to login with SSH from your terminal. Select <strong>Create a new key pair</strong> and then give it a name (in this case “debug_tutorial”). Then download the key pair, remove the .txt extension from the file and put it in the certificates folder. We will come back there later.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*-KhlnoFcxiCS3VQVlHPQ3Q.png" /></figure><p>Done. A green success message should appear on the page. Your instance is now running on the cloud. The problem is that anything will be loaded since it is empty. Let’s fill it up!</p><p>First of all, we need the CLI (Command Line Interface) for Amazon AWS. Open again the terminal and, using Homebrew, the only command you need to run is:</p><p>$ brew install awscli</p><p>Once it is done, you have to configure your <em>aws</em> details with:</p><p>$ aws configure</p><p>The first input you will need is your Access Key ID, that you can find by clicking on your name in the menu on the top right, and then on “My Security Credentials”. There, select Access key, create one and download the file. Put the downloaded file in the <em>certificates</em> folder. Now you have two keys: the <strong>Access Key ID</strong> and the <strong>Secret Key</strong>. The next data you will need for the configuration is the <strong>Default region name</strong> that needs to reflect the region you selected in the beginning (in our case is <em>us-west-1</em>). Here you can find a list of available regions:</p><pre>ap-northeast-1 - Asia Pacific (Tokyo)<br>ap-northeast-2 - Asia Pacific (Seoul)<br>ap-south-1 - Asia Pacific (Mumbai)<br>ap-southeast-1 - Asia Pacific (Singapore)<br>ap-southeast-2 - Asia Pacific (Sydney)<br>ca-central-1 - Canada (Central)<br>eu-central-1 - EU Central (Frankfurt)<br>eu-west-1 - EU West (Ireland)<br>eu-west-2 - EU West (London)<br>eu-west-3 - EU West (Paris)<br>sa-east-1 - South America (Sao Paulo)<br>us-east-1 - US East (Virginia)<br>us-east-2 - US East (Ohio)<br>us-west-1 - US West (N. California)<br>us-west-2 - US West (Oregon)</pre><p>Set <strong>Data output format</strong> as <em>text</em> and the configuration is done. Now you need to connect to your instance through SSH. To do this you need to run the command below, where <em>i-0f2103a2a2417f4cd</em> is the id of your instance.</p><p>$ aws ec2 get-console-output --instance-id i-0f2103a2a2417f4cd</p><p>In Terminal change directories to the <em>certificates</em> folder that contains the .pem file created earlier. In here you have to run this command, where debug_tutorial is the name of your certificate.</p><p>$ chmod 400 debug_tutorial.pem</p><p>Let’s connect to the instance finally! Run this command:</p><p>$ ssh -i debug_tutorial.pem ec2-user@ec2-13-57-229-28.us-west-1.compute.amazonaws.com</p><p>Since we selected “Linux “ at the beginning, the user is <em>ec2-user.</em> After the @, the DNS name is the Public DNS that you can find in the description of the instance. The debug_tutorial.pem, instead, is the name of your certificate. After this, enter yes and everything is set.</p><p>Now you are connected through SSH to your instance. It’s time to install docker on the machine:</p><pre>sudo yum update -y<br>sudo amazon-linux-extras install docker</pre><p>Start the docker service:</p><pre>sudo service docker start<br>sudo usermod -a -G docker ec2-user</pre><p>Logout with logout and log back in and then check the docker’s installation:</p><pre>docker info</pre><p>Now install and run the two containers:</p><pre>docker run -p 5432:5432 username/mydatabase:v1<br>docker run -p 8080:8080 -e DATABASE_URL=&#39;&#39; username/mybackend:v1</pre><blockquote><em>The DATABASE</em>_<em>URL is the public IP of your instance.</em></blockquote><p>Everything is up and running! Congratulations! Now you can access your API through the public IP address.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/1024/1*jl-9yDcFkR964GiHJyN-yw.png" /></figure><figure><img alt="" src="https://cdn-images-1.medium.com/proxy/1*ljTFIMmjzU5_IxkLssllAA.gif" /></figure><img src="https://medium.com/_/stat?event=post.clientViewed&referrerSource=full_rss&postId=ea9213518c43" width="1" height="1" alt="">]]></content:encoded>
        </item>
    </channel>
</rss>