SlideShare une entreprise Scribd logo
1  sur  98
Swift dans la vraie vie
#XebiConFr
Swift dans la vraie vie
Fabien Mirault
Développeur Objective-C / Swift
Speakers
@viteinfinite
Simone Civetta
Développeur Objective-C / Swift
@magici1
Swift ou pas ?
#XebiConFr
Swift dans la vraie vie
Septembre 2014
Octobre 2014
Novembre 2014
Juin 2014
Apple annonce Swift
!
Swift 1.0
!
Première application Swift
Xebia sur l’App Store
Swift 1.1
?
Janvier 2015
Nouvelles applications ?
Swift ou pas ?
Qu’est-ce que Swift ?
#XebiConFr
Swift dans la vraie vie
Nouveau langage de développement
Code plus lisible et moins verbeux
Donc plus simple à maintenir !
Qu’est-ce que Swift ?
#XebiConFr
Swift dans la vraie vie
Qu’est-ce que Swift ?
Transition Objective-C → Swift aisée
Moins de tolérance sur les erreurs de code
Rapidité de développement accrue
Swift ou pas ?
#XebiConFr
Swift dans la vraie vie
Septembre 2014
Octobre 2014
Novembre 2014
Juin 2014
Apple annonce Swift
!
Swift 1.0
!
Première application Xebia
sur l’App Store
Swift 1.1
?
Janvier 2015
Nouvelles applications !
!
Swift ou pas ?
Swift c’est cool……utilisé dans de vrais projets !
#XebiConFr
Swift dans la vraie vie
TOC
Nos cas d’usage
Flux d’activité
Création du projet et configuration
Produits et synchronisation
Langues
Commentaires
Testing
Suivre son application
Et l’Objective-C ?
Création du projet
#XebiConFr
Swift dans la vraie vie
Création du projet
Les dépendances
Librairies dynamiques
#XebiConFr
Swift dans la vraie vie
14
Slide Title
Title
Au revoir iOS 7
#XebiConFr
Swift dans la vraie vie
Création du projet
Les dépendances
Flux d’activités
#XebiConFr
Swift dans la vraie vie
Photos et vidéos
Fluidité
Des milliers de posts
Flux d’activités
#XebiConFr
Swift dans la vraie vie
Ne contient que ce qui a été défini
Meilleures performances
Stockage de type valeur et non référence
Struct
Flux d’activités
#XebiConFr
Swift dans la vraie vie
Flux d’activités
Exemple de Struct
public struct Attachment {
public let id: Int
public let url: String
public let type: String
public let name: String
public let objectId: Int
public let mimeType: String
public let objectType: String
}
Flux d’activités
#XebiConFr
Swift dans la vraie vie
Struct : Performances
Flux d’activités
Avec une méthode de shuffle sur 1.000.000 d’objets
Secondes
0
0,325
0,65
0,975
1,3
NSObject Struct
0,064
1,152
#XebiConFr
Swift dans la vraie vie
Flux d’activités
Struct VS Classes
Ne peut pas hériter d’objets
Pas de deinitializer
Référence unique d’une instance
#XebiConFr
Swift dans la vraie vie
Mapping automatique
Génère des structs
Performances accrues
JSONJoy
Flux d’activités
#XebiConFr
Swift dans la vraie vie
Flux d’activités
JSONJoy par l’exemple
private static func buildUser(userData:[String: AnyObject]) -> User? {
...
let user = User(JSONDecoder(userData))
return user
}
#XebiConFr
Swift dans la vraie vie
Flux d’activités
Crash
Flux d’activités
#XebiConFr
Swift dans la vraie vie
Flux d’activités
Struct
Héritage Rendu
Performances
Configurations
#XebiConFr
Swift dans la vraie vie
Analytics
Endpoints
Regroupement
Profil
Configurations
#XebiConFr
Swift dans la vraie vie
Configurations
struct Tags {
struct Page {
static let Login = "Login"
static let Camera = "Camera"
static let Newsfeed = "Newsfeed"
static let Favorites = "Favorites"
static let MyProfile = "MyProfile"
static let OtherProfile = "OtherProfile"
static let LiveSessions = "LiveSessions"
static let CreateAccount = "CreateAccount"
static let ForgottenPassword = "ForgottenPassword"
}
}
Configurations
Liste de produits
#XebiConFr
Swift dans la vraie vie
Liste de produits
200.000+ lignes!
Requêtes rapides!
#XebiConFr
Swift dans la vraie vie
Liste de produits
@implementation XBEntityStore
- (void)addEntity:(id<XBEntity>)entity {
// Some implementation
}
@end
...
Un peu d’Objective-C
- (void)addSomeObjects {
XBEntityStore *productStore = [XBEntityStore new];
// XBProduct conforms to XBEntity
XBProduct *product = [XBProduct new];
[productStore addEntity:product];
}
Stockage : Objective-C
#XebiConFr
Swift dans la vraie vie
- (void)addSomeObjects {
XBEntityStore *productStore = [XBEntityStore new];
// XBProduct conforms to XBEntity
XBProduct *product = [XBProduct new];
[productStore addEntity:product];
// XBColor conforms to XBEntity
XBColor *color = [XBColor new];
[productStore addEntity:color];
}
32
Liste de produits
Stockage : Objective-C
@implementation XBEntityStore
- (void)addEntity:(id<XBEntity>)entity {
// Some implementation
}
@end
...
Un peu d’Objective-C
#XebiConFr
Swift dans la vraie vie
33
Liste de produits
Generics
class EntityStore<T: Entity> {
func addEntity(entity: T) {
// Some implementation
}
}
...
func addSomeObjects() {
let productStore = EntityStore<Product>()
// Product conforms to Entity
let product = Product()
productStore.addEntity(product)
// Color conforms to Entity
let color = Color()
productStore.addEntity(color)
}
Un peu de Swift
func addSomeObjects() {
let productStore = EntityStore<Product>()
// Product conforms to Entity
let product = Product()
productStore.addEntity(product)
// Color conforms to Entity
let color = Color()
productStore.addEntity(color) // Ne compile pas !
}
#XebiConFr
Swift dans la vraie vie
34
Liste de produits
Generics
Écrire du code facilement réutilisable
et sujet à des contraintes spécifiques
#XebiConFr
Swift dans la vraie vie
35
Liste de produits
TypeAlias
typealias ProductStore = EntityStore<Product>
func addSomeObjects() {
let productStore = ProductStore()
// Product conforms to Entity
let product = Product()
productStore.addEntity(product)
}
typealias ColorStore = EntityStore<Color>
func addSomeObjects() {
let colorStore = ColorStore()
// Color conforms to Entity
let color = Color()
colorStore.addEntity(product)
}
Code plus expressif
#XebiConFr
Swift dans la vraie vie
36
Liste de produits
Protocols
Swift est un “langage orienté protocoles”
Apple, 2015
protocol Entity { }
class EntityStore<T: Entity> {
func addEntity(entity: T) {
// Some implementation
}
}
#XebiConFr
Swift dans la vraie vie
37
Liste de produits
Swift VS Swift
class EntityStore {
func addEntity(entity: Entity) {
// Some implementation
}
}
func addSomeObjects() {
let productStore = EntityStore()
let product = Product()
productStore.addEntity(product)
}
Coder Swift != Penser Swift
class EntityStore<T: Entity> {
func addEntity(entity: T) {
// Some implementation
}
}
func addSomeObjects() {
let productStore = ProductStore()
let product = Product()
productStore.addEntity(product)
}
Generics
Typealias
Synchronisation
#XebiConFr
Swift dans la vraie vie
Synchronisation
Synchronisation et
manipulation*
500 Mo de données
!
200.000+ éléments!
Performances!
#XebiConFr
Swift dans la vraie vie
Synchronisation
déclarations final et static
Profiter pleinement du dispatch statique
Performances
#XebiConFr
Swift dans la vraie vie
Synchronisation
Attention aux casts entre
Array ↔ NSArray
Dictionary ↔ NSDictionary
Performances
Tâches asynchrones
#XebiConFr
Swift dans la vraie vie
Librairie locale
Appareil photo
Ecran personnalisé
Animation diaphragme
Tâches asynchrones
#XebiConFr
Swift dans la vraie vie
Tâches asynchrones
Equivalent des blocks en Objective-C
Comprend un bloc de code à exécuter
Définition : {	
  ()	
  -­‐>	
  ()	
  in	
  }
Closure
#XebiConFr
Swift dans la vraie vie
Tâches asynchrones
Exemple de closure
self.closeDiaphragm(duration:0.3, completionBlock: { finished in
self.openDiaphragm(duration:0.3)
})
#XebiConFr
Swift dans la vraie vie
Tâches asynchrones
Optional
Possède une valeur ou non
Sécurise le code
Tester la non nullité : if	
  let
Définition : var	
  delegate:CameraDelegate?
#XebiConFr
Swift dans la vraie vie
Tâches asynchrones
Exemple d’optionals
func setup(image:UIImage?) {
if let menuIcon = image {
let menuImageView = UIImageView(image: menuIcon)
self.addSubview(menuImageView)
}
}
#XebiConFr
Swift dans la vraie vie
48
Tâches asynchrones
Optionals : fiabilité !
#XebiConFr
Swift dans la vraie vie
Appels asynchrones
Poster un commentaire
Sur n’importe quel post
Gestion des retours serveur
Tâches asynchrones
#XebiConFr
Swift dans la vraie vie
Tâches asynchrones
Promise
Code plus lisible
Idéal pour les tâches asynchrones
Chaînage possible
#XebiConFr
Swift dans la vraie vie
Tâches asynchrones
Exemple de Promise
// Parameters
var parameters = Parameters()
parameters["content"] = view.textView.text
PostRequest.getHeaders()
.success { token in
return PostRequest.postContent(token, parameters)
}
.success { data in
sendComplete()
}
.failure { (error, isCancelled) -> Void in
sendFailed()
}
#XebiConFr
Swift dans la vraie vie
Tâches asynchrones
Sans Promise
// Parameters
var parameters = Parameters()
parameters["content"] = view.textView.text
PostRequest.getHeaders() { [weak self] (token:String, error:NSError) -> Void in
if token != nil {
PostRequest.postContent(token, parameters) { [weak self] (result:Bool, error:NSError) -> Void in
if result == true {
if let strongSelf == self {
strongSelf.sendComplete()
}
} else {
if let strongSelf == self {
strongSelf.sendFailed()
}
}
}
} else {
if let strongSelf == self {
strongSelf.sendFailed()
}
}
}
#XebiConFr
Swift dans la vraie vie
SwiftTasks
Librairie principale
Mise en place simple…
…mais des erreurs dans Xcode
#XebiConFr
Swift dans la vraie vie
Tâches asynchrones
Erreurs avec Xcode
if let colorsFilePath = syncDataConfiguration.colorsFile, data = NSData(contentsOfFile:colorsFilePath) {
MetadataJSONDeserializer.deserialize(data, keyPath: "colors.color")
.success { color -> ColorDuplicateRemovalTask in
return self.removeDuplicateIdentifiers(colors)
}
.success { colors -> JSONInsertTask in
return entityStore.replaceAllObjects(colors, transformer: Color.tranform)
}
.success { JSONs -> Void in
taskTuple.fulfill(JSONs)
}
.failure { (error, isCancelled) in
if let error = error {
taskTuple.reject(error)
}
}
return taskTuple.task
}
Disponibilité produit
#XebiConFr
Swift dans la vraie vie
Disponibilité produit
Simple requête HTTP!
Mise à jour de la UI!
#XebiConFr
Swift dans la vraie vie
Disponibilité produit
Alamofire
Alamofire.request(URLRequest)
.validate()
.response { (request, response, data, error) in
print(request)
print(response)
print(data)
print(error)
}
#XebiConFr
Swift dans la vraie vie
Disponibilité produit
Les étapes
WebService
Déserialisation
UI
#XebiConFr
Swift dans la vraie vie
59
Disponibilité produit
Functional Reactive Programming
Propagation des changements
Flux de données
Asynchronisme
#XebiConFr
Swift dans la vraie vie
ReactiveCocoa
Reactive Cocoa
Disponibilité produit
#XebiConFr
Swift dans la vraie vie
ReactKit
github.com/ReactKit/
Disponibilité produit
#XebiConFr
Swift dans la vraie vie
Disponibilité produit
Functional Reactive Programming
^{
let available = $0 as! Bool
self.availabilitySpinner.stopAnimating()
self.availabilityIndicator.textColor = self.colorForStatus(available)
} <~ KVO.signal(viewModel, "status")
#XebiConFr
Swift dans la vraie vie
[[[RACObserve(viewModel.status)
map:^id(NSString *status) {
if ([status isKindOfClass:[NSString class]]) {
return status;
}
return nil;
}]
map:^id(NSString *status) {
return @([status isEqualToString:@“available"]);
}]
delay:1.0];
[[[RACObserve(viewModel.status)
map:^id(NSString *status) {
if ([status isKindOfClass:[NSString class]]) {
return status;
}
return nil;
}]
map:^id(NSString *status) {
return @([status isEqualToString:@“available"]);
}]
delay:1.0];
Disponibilité produit
FRP - Objective-C
#XebiConFr
Swift dans la vraie vie
Disponibilité produit
FRP - Swift
let availabilitySignal = KVO.signal(viewModel, "status")
.map { status -> String? in
return status as? String
}
.map { status -> Bool in
return status == "available"
}
.delay(1.0)
#XebiConFr
Swift dans la vraie vie
Disponibilité produit
Opérateurs Custom
^{
self.availabilitySpinner.stopAnimating()
self.availabilityIndicator.textColor = self.colorForStatus($0)
} <~ availabilitySignal<~
#XebiConFr
Swift dans la vraie vie
Slide Title
Title
Internationalisation
#XebiConFr
Swift dans la vraie vie
Internationalisation
Changement de la langue!
Traduction des contenus!
Traduction de l’IHM!
#XebiConFr
Swift dans la vraie vie
Internationalisation
self.headerLabel.text = NSLocalizedString("Header.Title", comment: "Header Title")
extension UILabel {
var localizedText: String {
set {
self.text = NSLocalizedString(newValue, comment: newValue)
}
/* ... */
}
}
self.headerLabel.localizedText = "Header.Title"
Extensions
#XebiConFr
Swift dans la vraie vie
70
Internationalisation
Enums
typedef enum : NSUInteger {
XBCountryUSA,
XBCountryChina,
XBCountryItaly
} XBCountry;
Un peu d’Objective-C
#XebiConFr
Swift dans la vraie vie
71
Internationalisation
Enums
enum Country: String {
case USA = "US"
case China = "CN"
case Italy = "IT"
}
Et finalement du Swift
Valeurs associées
#XebiConFr
Swift dans la vraie vie
72
Internationalisation
Enums
enum Country: String {
case USA = "US"
case China = "CN"
case Italy = "IT"
static var defaultCountry: Country {
return Country.Italy
}
}
Country.defaultCountry
Et finalement du Swift
Valeurs associées
Propriétés
#XebiConFr
Swift dans la vraie vie
73
Internationalisation
Switch
enum Language {
case English(region: String)
case Italian
var name: String {
switch self {
case .English(let region):
return "English " + region
case .Italian:
return "Italian"
}
}
}
Swift
#XebiConFr
Swift dans la vraie vie
74
Internationalisation
Switch
enum Language {
case English(region: String)
case Italian
var name: String {
switch self {
case .English(let region):
return "English " + region
case .Italian:
return "Italian"
}
}
}
Swift
Pattern matching
#XebiConFr
Swift dans la vraie vie
enum Language {
case English(region: String)
case Italian
var name: String {
switch self {
case .English(let region)
where region == "US":
return "English Default”
case .English(let region):
return "English " + region
case .Italian:
return "Italian"
}
}
75
Internationalisation
Switch
Swift
Pattern matching
Switch exhaustif
#XebiConFr
Swift dans la vraie vie
Internationalisation
Enums : it’s over 9000!!
First-Class citizens
Méthodes et propriétés
Valeurs associées
Tests
#XebiConFr
Swift dans la vraie vie
Tests
Assurer le fonctionnement
de l’application
Se protéger des régressions
#XebiConFr
Swift dans la vraie vie
Tests
Stockage des produits
static func processProducts(products: [Product]) {
products.filter { ... }
Stores.ProductStore.insertObjects(products)
}
...
processProducts(myProducts)
func testProcessProducts() {
// Setup
let products = [Product("A"), Product("B")]
let productManager = ProductManager()
// Run
productManager.processProducts(products)
// Verify
// ??
}
Comment tester ?
#XebiConFr
Swift dans la vraie vie
80
Tests
Stockage des produits
func testProcessProducts() {
// Setup
let products = [Product("A"), Product("B")]
let mockProductStore = ProductStore(coordinator: MockCoordinator())
let productManager = ProductManager()
// Run
productManager.processProducts(products, productStore: mockProductStore)
// Verify
XCTAssertEqual(productStore.allObjects().count, 2)
}
func processProducts(products: [Product], productStore: ProductStore = ProductStore()) {
products.filter { ... }
productStore.insertObjects(products)
}
...
processProducts(myProducts)
#XebiConFr
Swift dans la vraie vie
81
Slide Title
Title
#XebiConFr
Swift dans la vraie vie
82
Tests
Mais aussi…
#XebiConFr
Swift dans la vraie vie
83
Tests
Mais aussi…
#XebiConFr
Swift dans la vraie vie
84
Tests
Mais aussi…
Suivre son application
#XebiConFr
Swift dans la vraie vie
Suivre son application
Déploiement centralisé et versionné
Remontées de crashs
Statistiques d’utilisation
Fabric
#XebiConFr
Swift dans la vraie vie
Suivre son application
Fabric - Objective-C
RTSViewController.m line 1310
-[RTSViewController getCurrentUDPValues]
Fatal Exception: NSRangeException
*** -[__NSArrayM objectAtIndex:]
index 4294967292 beyond bounds [0 .. 511]
#XebiConFr
Swift dans la vraie vie
Suivre son application
Fabric - Swift
WSClient.swift line 31
static MyLittlePony.WSClient.requestContent
(MyLittlePony.WSClient.Type) parameters : Swift.Optional
<Swift.Dictionary <Swift.String, Swift.AnyObject>
Crashed: com.apple.main-thread
SIGABRT ABORT at 0x312a8df0
#XebiConFr
Swift dans la vraie vie
Suivre son application
Reveal
Vue éclatée
Fonctionne sur simulateur ou device
Édition à la volée des propriétés
#XebiConFr
Swift dans la vraie vie
Suivre son application
Reveal
#XebiConFr
Swift dans la vraie vie
Suivre son application
Suivre son application
Évolution du langage constante
Rétrocompatibilité non assurée
Et l’Objective-C ?
#XebiConFr
Swift dans la vraie vie
Toujours valable
Mais développement plus lent
Migration progressive conseillée
Et l’Objective-C dans tout ça ?
#XebiConFr
Swift dans la vraie vie
Popularitédesrecherches
2014 2015
Objective-C Swift Objective-C Swift
Source : TIOBE
3 ème
19 ème
14 ème
15 ème
Et l’Objective-C dans tout ça ?
#XebiConFr
Swift dans la vraie vieNouveaux Repositories entre Q3 et Q4 2014
Swift Objective-C
97
3757
Source : http://githut.info
Et l’Objective-C dans tout ça ?
#XebiConFr
Swift dans la vraie vie
Les avantages de Swift
Plus facile à maintenir et plus robuste
Demande moins de code
Soyez acteur des évolutions d’Apple !
#XebiConFr
Swift dans la vraie vie
#XebiConFr
Swift dans la vraie vie
Un peu de lecture
A Swift Kickstart

Daniel Steinberg
Functional Programming in Swift

Chris Eidhof, Florian Kugler, and Wouter Swierstra
http://blog.xebia.fr/tag/swift
L’équipe iOS Xebia
Advanced Swift

Chris Eidhof and Airspeed Velocity

Contenu connexe

Tendances

SPA avec Angular et SignalR (FR)
SPA avec Angular et SignalR (FR)SPA avec Angular et SignalR (FR)
SPA avec Angular et SignalR (FR)Rui Carvalho
 
CocoaHeads Toulouse - Xcode et les tests - Epitez
CocoaHeads Toulouse - Xcode et les tests - EpitezCocoaHeads Toulouse - Xcode et les tests - Epitez
CocoaHeads Toulouse - Xcode et les tests - EpitezCocoaHeads France
 
Node.js, le pavé dans la mare
Node.js, le pavé dans la mareNode.js, le pavé dans la mare
Node.js, le pavé dans la mareValtech
 
Introduction TypeScript
Introduction TypeScriptIntroduction TypeScript
Introduction TypeScriptfelixbillon
 
Déploiement PHP : de l'âge de pierre à nos jours.
Déploiement PHP : de l'âge de pierre à nos jours.Déploiement PHP : de l'âge de pierre à nos jours.
Déploiement PHP : de l'âge de pierre à nos jours.Amélie DUVERNET
 
Intégration continue des projets PHP avec Jenkins
Intégration continue des projets PHP avec JenkinsIntégration continue des projets PHP avec Jenkins
Intégration continue des projets PHP avec JenkinsHugo Hamon
 
Django pour les développeurs Symfony (et réciproquement)
Django pour les développeurs Symfony (et réciproquement)Django pour les développeurs Symfony (et réciproquement)
Django pour les développeurs Symfony (et réciproquement)Nicolas Perriault
 
Du JavaScript propre ? Challenge accepted ! @Devoxx France 2013
Du JavaScript propre ? Challenge accepted ! @Devoxx France 2013Du JavaScript propre ? Challenge accepted ! @Devoxx France 2013
Du JavaScript propre ? Challenge accepted ! @Devoxx France 2013Julien Jakubowski
 
Javascript pour le développeur Java
Javascript pour le développeur JavaJavascript pour le développeur Java
Javascript pour le développeur Javajollivetc
 
Présentation JavaScript
Présentation JavaScriptPrésentation JavaScript
Présentation JavaScripttarkan_
 
TypeScript for dummies
TypeScript for dummiesTypeScript for dummies
TypeScript for dummiesMicrosoft
 
Partie1 TypeScript
Partie1 TypeScriptPartie1 TypeScript
Partie1 TypeScriptHabib Ayad
 
Pourquoi et comment j'ai appris JavaScript
Pourquoi et comment j'ai appris JavaScriptPourquoi et comment j'ai appris JavaScript
Pourquoi et comment j'ai appris JavaScriptjollivetc
 
Petit déjeuner OCTO Technology - Nouvelles Architectures Web Front-End et APIs
Petit déjeuner OCTO Technology - Nouvelles Architectures Web Front-End et APIsPetit déjeuner OCTO Technology - Nouvelles Architectures Web Front-End et APIs
Petit déjeuner OCTO Technology - Nouvelles Architectures Web Front-End et APIsOCTO Technology
 
Partie 2: Angular
Partie 2: AngularPartie 2: Angular
Partie 2: AngularHabib Ayad
 
Orchestrez vos projets Symfony sans fausses notes
Orchestrez vos projets Symfony sans fausses notesOrchestrez vos projets Symfony sans fausses notes
Orchestrez vos projets Symfony sans fausses notesXavier Gorse
 
PHP 7.0 : aperçu des nouveautés
PHP 7.0 : aperçu des nouveautésPHP 7.0 : aperçu des nouveautés
PHP 7.0 : aperçu des nouveautésDidcode
 
Gatekeeper par Guillaume Faure
Gatekeeper par Guillaume FaureGatekeeper par Guillaume Faure
Gatekeeper par Guillaume FaureCocoaHeads France
 

Tendances (20)

SPA avec Angular et SignalR (FR)
SPA avec Angular et SignalR (FR)SPA avec Angular et SignalR (FR)
SPA avec Angular et SignalR (FR)
 
CocoaHeads Toulouse - Xcode et les tests - Epitez
CocoaHeads Toulouse - Xcode et les tests - EpitezCocoaHeads Toulouse - Xcode et les tests - Epitez
CocoaHeads Toulouse - Xcode et les tests - Epitez
 
Devoxx France - Nouvelles du Front
Devoxx France - Nouvelles du FrontDevoxx France - Nouvelles du Front
Devoxx France - Nouvelles du Front
 
Node.js, le pavé dans la mare
Node.js, le pavé dans la mareNode.js, le pavé dans la mare
Node.js, le pavé dans la mare
 
Introduction TypeScript
Introduction TypeScriptIntroduction TypeScript
Introduction TypeScript
 
Déploiement PHP : de l'âge de pierre à nos jours.
Déploiement PHP : de l'âge de pierre à nos jours.Déploiement PHP : de l'âge de pierre à nos jours.
Déploiement PHP : de l'âge de pierre à nos jours.
 
Intégration continue des projets PHP avec Jenkins
Intégration continue des projets PHP avec JenkinsIntégration continue des projets PHP avec Jenkins
Intégration continue des projets PHP avec Jenkins
 
Dynamic Languages
Dynamic LanguagesDynamic Languages
Dynamic Languages
 
Django pour les développeurs Symfony (et réciproquement)
Django pour les développeurs Symfony (et réciproquement)Django pour les développeurs Symfony (et réciproquement)
Django pour les développeurs Symfony (et réciproquement)
 
Du JavaScript propre ? Challenge accepted ! @Devoxx France 2013
Du JavaScript propre ? Challenge accepted ! @Devoxx France 2013Du JavaScript propre ? Challenge accepted ! @Devoxx France 2013
Du JavaScript propre ? Challenge accepted ! @Devoxx France 2013
 
Javascript pour le développeur Java
Javascript pour le développeur JavaJavascript pour le développeur Java
Javascript pour le développeur Java
 
Présentation JavaScript
Présentation JavaScriptPrésentation JavaScript
Présentation JavaScript
 
TypeScript for dummies
TypeScript for dummiesTypeScript for dummies
TypeScript for dummies
 
Partie1 TypeScript
Partie1 TypeScriptPartie1 TypeScript
Partie1 TypeScript
 
Pourquoi et comment j'ai appris JavaScript
Pourquoi et comment j'ai appris JavaScriptPourquoi et comment j'ai appris JavaScript
Pourquoi et comment j'ai appris JavaScript
 
Petit déjeuner OCTO Technology - Nouvelles Architectures Web Front-End et APIs
Petit déjeuner OCTO Technology - Nouvelles Architectures Web Front-End et APIsPetit déjeuner OCTO Technology - Nouvelles Architectures Web Front-End et APIs
Petit déjeuner OCTO Technology - Nouvelles Architectures Web Front-End et APIs
 
Partie 2: Angular
Partie 2: AngularPartie 2: Angular
Partie 2: Angular
 
Orchestrez vos projets Symfony sans fausses notes
Orchestrez vos projets Symfony sans fausses notesOrchestrez vos projets Symfony sans fausses notes
Orchestrez vos projets Symfony sans fausses notes
 
PHP 7.0 : aperçu des nouveautés
PHP 7.0 : aperçu des nouveautésPHP 7.0 : aperçu des nouveautés
PHP 7.0 : aperçu des nouveautés
 
Gatekeeper par Guillaume Faure
Gatekeeper par Guillaume FaureGatekeeper par Guillaume Faure
Gatekeeper par Guillaume Faure
 

En vedette

Open XKE - De l'intégration continue au déploiement continu sur iOS et Androi...
Open XKE - De l'intégration continue au déploiement continu sur iOS et Androi...Open XKE - De l'intégration continue au déploiement continu sur iOS et Androi...
Open XKE - De l'intégration continue au déploiement continu sur iOS et Androi...Publicis Sapient Engineering
 
Xcode formation-iphone-ipad-xcode-et-cocoa
Xcode formation-iphone-ipad-xcode-et-cocoaXcode formation-iphone-ipad-xcode-et-cocoa
Xcode formation-iphone-ipad-xcode-et-cocoaCERTyou Formation
 
DevOps - Retour d’expérience - RivieraDev du 20 Octobre 2011
DevOps - Retour d’expérience - RivieraDev du 20 Octobre 2011DevOps - Retour d’expérience - RivieraDev du 20 Octobre 2011
DevOps - Retour d’expérience - RivieraDev du 20 Octobre 2011Henri Gomez
 
Comment concilier Agilité et projet au forfait ?
Comment concilier Agilité et projet au forfait ?Comment concilier Agilité et projet au forfait ?
Comment concilier Agilité et projet au forfait ?Lorraine JUG
 
Xcode Server - Jeffrey Macko
Xcode Server - Jeffrey MackoXcode Server - Jeffrey Macko
Xcode Server - Jeffrey MackoCocoaHeads France
 
Automate your build on Android with Jenkins
Automate your build on Android with JenkinsAutomate your build on Android with Jenkins
Automate your build on Android with JenkinsBeMyApp
 
Spec et test agile sur mobile @airfrance #at lille & cocoaheads tls
Spec et test agile sur mobile @airfrance #at lille & cocoaheads tlsSpec et test agile sur mobile @airfrance #at lille & cocoaheads tls
Spec et test agile sur mobile @airfrance #at lille & cocoaheads tlsekito
 
SWIFT Standards developer kit tutorial December 2012
SWIFT Standards developer kit tutorial December 2012SWIFT Standards developer kit tutorial December 2012
SWIFT Standards developer kit tutorial December 2012Ed Dodds
 
Use In IoT : l’objet connecté de la board au dashboard
Use In IoT : l’objet connecté de la board au dashboardUse In IoT : l’objet connecté de la board au dashboard
Use In IoT : l’objet connecté de la board au dashboardMicrosoft
 
Tipos de Brackets- Introducción a la Odontología
Tipos de Brackets- Introducción a la OdontologíaTipos de Brackets- Introducción a la Odontología
Tipos de Brackets- Introducción a la Odontologíacrisppg
 
9 tendances du Mobile World Congress 2017 par @hubinstitute
9 tendances du Mobile World Congress 2017 par @hubinstitute 9 tendances du Mobile World Congress 2017 par @hubinstitute
9 tendances du Mobile World Congress 2017 par @hubinstitute HUB INSTITUTE
 
Infrastructure as code: running microservices on AWS using Docker, Terraform,...
Infrastructure as code: running microservices on AWS using Docker, Terraform,...Infrastructure as code: running microservices on AWS using Docker, Terraform,...
Infrastructure as code: running microservices on AWS using Docker, Terraform,...Yevgeniy Brikman
 
Informatique_Libertés_Identités
Informatique_Libertés_IdentitésInformatique_Libertés_Identités
Informatique_Libertés_IdentitésFing
 
Precise
PrecisePrecise
Precisezust
 
BOUILLON, Jean - Luc (2007). ""L'impensé communicationnel" dans la coodinatio...
BOUILLON, Jean - Luc (2007). ""L'impensé communicationnel" dans la coodinatio...BOUILLON, Jean - Luc (2007). ""L'impensé communicationnel" dans la coodinatio...
BOUILLON, Jean - Luc (2007). ""L'impensé communicationnel" dans la coodinatio...Romain Trillard
 

En vedette (20)

Open XKE - De l'intégration continue au déploiement continu sur iOS et Androi...
Open XKE - De l'intégration continue au déploiement continu sur iOS et Androi...Open XKE - De l'intégration continue au déploiement continu sur iOS et Androi...
Open XKE - De l'intégration continue au déploiement continu sur iOS et Androi...
 
Xcode formation-iphone-ipad-xcode-et-cocoa
Xcode formation-iphone-ipad-xcode-et-cocoaXcode formation-iphone-ipad-xcode-et-cocoa
Xcode formation-iphone-ipad-xcode-et-cocoa
 
DevOps - Retour d’expérience - RivieraDev du 20 Octobre 2011
DevOps - Retour d’expérience - RivieraDev du 20 Octobre 2011DevOps - Retour d’expérience - RivieraDev du 20 Octobre 2011
DevOps - Retour d’expérience - RivieraDev du 20 Octobre 2011
 
Comment concilier Agilité et projet au forfait ?
Comment concilier Agilité et projet au forfait ?Comment concilier Agilité et projet au forfait ?
Comment concilier Agilité et projet au forfait ?
 
Xcode Server - Jeffrey Macko
Xcode Server - Jeffrey MackoXcode Server - Jeffrey Macko
Xcode Server - Jeffrey Macko
 
Automate your build on Android with Jenkins
Automate your build on Android with JenkinsAutomate your build on Android with Jenkins
Automate your build on Android with Jenkins
 
Spec et test agile sur mobile @airfrance #at lille & cocoaheads tls
Spec et test agile sur mobile @airfrance #at lille & cocoaheads tlsSpec et test agile sur mobile @airfrance #at lille & cocoaheads tls
Spec et test agile sur mobile @airfrance #at lille & cocoaheads tls
 
SWIFT Standards developer kit tutorial December 2012
SWIFT Standards developer kit tutorial December 2012SWIFT Standards developer kit tutorial December 2012
SWIFT Standards developer kit tutorial December 2012
 
Use In IoT : l’objet connecté de la board au dashboard
Use In IoT : l’objet connecté de la board au dashboardUse In IoT : l’objet connecté de la board au dashboard
Use In IoT : l’objet connecté de la board au dashboard
 
Tipos de Brackets- Introducción a la Odontología
Tipos de Brackets- Introducción a la OdontologíaTipos de Brackets- Introducción a la Odontología
Tipos de Brackets- Introducción a la Odontología
 
IoT Best practices
 IoT Best practices IoT Best practices
IoT Best practices
 
9 tendances du Mobile World Congress 2017 par @hubinstitute
9 tendances du Mobile World Congress 2017 par @hubinstitute 9 tendances du Mobile World Congress 2017 par @hubinstitute
9 tendances du Mobile World Congress 2017 par @hubinstitute
 
Infrastructure as code: running microservices on AWS using Docker, Terraform,...
Infrastructure as code: running microservices on AWS using Docker, Terraform,...Infrastructure as code: running microservices on AWS using Docker, Terraform,...
Infrastructure as code: running microservices on AWS using Docker, Terraform,...
 
5 filosofia medieval
5 filosofia medieval5 filosofia medieval
5 filosofia medieval
 
Osgi ParisJUG 2008-10-14
Osgi ParisJUG 2008-10-14Osgi ParisJUG 2008-10-14
Osgi ParisJUG 2008-10-14
 
Informatique_Libertés_Identités
Informatique_Libertés_IdentitésInformatique_Libertés_Identités
Informatique_Libertés_Identités
 
Precise
PrecisePrecise
Precise
 
BOUILLON, Jean - Luc (2007). ""L'impensé communicationnel" dans la coodinatio...
BOUILLON, Jean - Luc (2007). ""L'impensé communicationnel" dans la coodinatio...BOUILLON, Jean - Luc (2007). ""L'impensé communicationnel" dans la coodinatio...
BOUILLON, Jean - Luc (2007). ""L'impensé communicationnel" dans la coodinatio...
 
CV Adam Fra V4
CV Adam Fra V4CV Adam Fra V4
CV Adam Fra V4
 
La sublimation
La sublimationLa sublimation
La sublimation
 

Similaire à XebiConFr 15 - Swift dans la vraie vie

Visual Studio 2008 Overview
Visual Studio 2008 OverviewVisual Studio 2008 Overview
Visual Studio 2008 OverviewGregory Renard
 
Initiation au développement mobile sous Android
Initiation au développement mobile sous AndroidInitiation au développement mobile sous Android
Initiation au développement mobile sous AndroidAbdelkader Rhouati
 
Code flow - Cocoaheads paris
Code flow - Cocoaheads parisCode flow - Cocoaheads paris
Code flow - Cocoaheads parisCocoaHeads France
 
Linq et Entity framework
Linq et Entity frameworkLinq et Entity framework
Linq et Entity frameworkDNG Consulting
 
Le Nouvel Ops XebiCon'15
Le Nouvel Ops XebiCon'15Le Nouvel Ops XebiCon'15
Le Nouvel Ops XebiCon'15Séven Le Mesle
 
Formation java script
Formation java scriptFormation java script
Formation java scriptRomdhani Asma
 
Environnement de développement de bases de données
Environnement de développement de bases de donnéesEnvironnement de développement de bases de données
Environnement de développement de bases de donnéesISIG
 
Environnement de développement de bases de données
Environnement de développement de bases de donnéesEnvironnement de développement de bases de données
Environnement de développement de bases de donnéesISIG
 
CocoaHeads Rennes #14: Programmation Responsive par Celedev
CocoaHeads Rennes #14: Programmation Responsive par CeledevCocoaHeads Rennes #14: Programmation Responsive par Celedev
CocoaHeads Rennes #14: Programmation Responsive par CeledevCocoaHeadsRNS
 
Kinect et Office365 : Un bon geste en faveur de votre SI
Kinect et Office365 : Un bon geste en faveur de votre SIKinect et Office365 : Un bon geste en faveur de votre SI
Kinect et Office365 : Un bon geste en faveur de votre SIFabrice BARBIN
 
Kinect + Office365 : Un bon geste en faveur de votre SI !
Kinect + Office365 : Un bon geste en faveur de votre SI ! Kinect + Office365 : Un bon geste en faveur de votre SI !
Kinect + Office365 : Un bon geste en faveur de votre SI ! Microsoft Technet France
 
Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0
Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0
Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0Gregory Renard
 
Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0
Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0
Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0Gregory Renard
 
react-slides.ppx (2) (1).pptx react presentation basic
react-slides.ppx (2) (1).pptx react presentation basicreact-slides.ppx (2) (1).pptx react presentation basic
react-slides.ppx (2) (1).pptx react presentation basiczineblahib2
 
Formation iPhone ENSI by (Orange Tunisie)
Formation iPhone ENSI by (Orange Tunisie)Formation iPhone ENSI by (Orange Tunisie)
Formation iPhone ENSI by (Orange Tunisie)Farouk Mezghich
 
Développer une application android en 2015
Développer une application android  en 2015Développer une application android  en 2015
Développer une application android en 2015Florent Champigny
 
Patterns and OOP in PHP
Patterns and OOP in PHPPatterns and OOP in PHP
Patterns and OOP in PHPjulien pauli
 
Conférence Titanium + Alloy au JUG Montpellier
Conférence Titanium + Alloy au JUG MontpellierConférence Titanium + Alloy au JUG Montpellier
Conférence Titanium + Alloy au JUG MontpellierDamien Laureaux
 

Similaire à XebiConFr 15 - Swift dans la vraie vie (20)

Visual Studio 2008 Overview
Visual Studio 2008 OverviewVisual Studio 2008 Overview
Visual Studio 2008 Overview
 
Initiation au développement mobile sous Android
Initiation au développement mobile sous AndroidInitiation au développement mobile sous Android
Initiation au développement mobile sous Android
 
Code flow - Cocoaheads paris
Code flow - Cocoaheads parisCode flow - Cocoaheads paris
Code flow - Cocoaheads paris
 
Linq et Entity framework
Linq et Entity frameworkLinq et Entity framework
Linq et Entity framework
 
Le Nouvel Ops XebiCon'15
Le Nouvel Ops XebiCon'15Le Nouvel Ops XebiCon'15
Le Nouvel Ops XebiCon'15
 
Formation java script
Formation java scriptFormation java script
Formation java script
 
Native script
Native scriptNative script
Native script
 
Environnement de développement de bases de données
Environnement de développement de bases de donnéesEnvironnement de développement de bases de données
Environnement de développement de bases de données
 
Environnement de développement de bases de données
Environnement de développement de bases de donnéesEnvironnement de développement de bases de données
Environnement de développement de bases de données
 
CocoaHeads Rennes #14: Programmation Responsive par Celedev
CocoaHeads Rennes #14: Programmation Responsive par CeledevCocoaHeads Rennes #14: Programmation Responsive par Celedev
CocoaHeads Rennes #14: Programmation Responsive par Celedev
 
Kinect et Office365 : Un bon geste en faveur de votre SI
Kinect et Office365 : Un bon geste en faveur de votre SIKinect et Office365 : Un bon geste en faveur de votre SI
Kinect et Office365 : Un bon geste en faveur de votre SI
 
Kinect + Office365 : Un bon geste en faveur de votre SI !
Kinect + Office365 : Un bon geste en faveur de votre SI ! Kinect + Office365 : Un bon geste en faveur de votre SI !
Kinect + Office365 : Un bon geste en faveur de votre SI !
 
Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0
Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0
Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0
 
Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0
Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0
Visual Basic 9.0 – Visual Studio 2008 Quoi De Neuf 2.0
 
react-slides.ppx (2) (1).pptx react presentation basic
react-slides.ppx (2) (1).pptx react presentation basicreact-slides.ppx (2) (1).pptx react presentation basic
react-slides.ppx (2) (1).pptx react presentation basic
 
Formation iPhone ENSI by (Orange Tunisie)
Formation iPhone ENSI by (Orange Tunisie)Formation iPhone ENSI by (Orange Tunisie)
Formation iPhone ENSI by (Orange Tunisie)
 
Développer une application android en 2015
Développer une application android  en 2015Développer une application android  en 2015
Développer une application android en 2015
 
Patterns and OOP in PHP
Patterns and OOP in PHPPatterns and OOP in PHP
Patterns and OOP in PHP
 
Compte rendu Blend Web Mix 2015
Compte rendu Blend Web Mix 2015Compte rendu Blend Web Mix 2015
Compte rendu Blend Web Mix 2015
 
Conférence Titanium + Alloy au JUG Montpellier
Conférence Titanium + Alloy au JUG MontpellierConférence Titanium + Alloy au JUG Montpellier
Conférence Titanium + Alloy au JUG Montpellier
 

Plus de Publicis Sapient Engineering

XebiCon'18 - L'algorithme de reconnaissance de formes par le cerveau humain
XebiCon'18 - L'algorithme de reconnaissance de formes par le cerveau humainXebiCon'18 - L'algorithme de reconnaissance de formes par le cerveau humain
XebiCon'18 - L'algorithme de reconnaissance de formes par le cerveau humainPublicis Sapient Engineering
 
Xebicon'18 - Spark in jail : conteneurisez vos traitements data sans serveur
Xebicon'18 - Spark in jail : conteneurisez vos traitements data sans serveurXebicon'18 - Spark in jail : conteneurisez vos traitements data sans serveur
Xebicon'18 - Spark in jail : conteneurisez vos traitements data sans serveurPublicis Sapient Engineering
 
XebiCon'18 - La Web App d'aujourd'hui et de demain : état de l'art et bleedin...
XebiCon'18 - La Web App d'aujourd'hui et de demain : état de l'art et bleedin...XebiCon'18 - La Web App d'aujourd'hui et de demain : état de l'art et bleedin...
XebiCon'18 - La Web App d'aujourd'hui et de demain : état de l'art et bleedin...Publicis Sapient Engineering
 
XebiCon'18 - Des notebook pour le monitoring avec Zeppelin
XebiCon'18 - Des notebook pour le monitoring avec Zeppelin XebiCon'18 - Des notebook pour le monitoring avec Zeppelin
XebiCon'18 - Des notebook pour le monitoring avec Zeppelin Publicis Sapient Engineering
 
XebiCon'18 - Event Sourcing et RGPD, incompatibles ?
XebiCon'18 - Event Sourcing et RGPD, incompatibles ?XebiCon'18 - Event Sourcing et RGPD, incompatibles ?
XebiCon'18 - Event Sourcing et RGPD, incompatibles ?Publicis Sapient Engineering
 
XebiCon'18 - Deno, le nouveau NodeJS qui inverse la tendance ?
XebiCon'18 - Deno, le nouveau NodeJS qui inverse la tendance ?XebiCon'18 - Deno, le nouveau NodeJS qui inverse la tendance ?
XebiCon'18 - Deno, le nouveau NodeJS qui inverse la tendance ?Publicis Sapient Engineering
 
XebiCon'18 - Boostez vos modèles avec du Deep Learning distribué
XebiCon'18 - Boostez vos modèles avec du Deep Learning distribuéXebiCon'18 - Boostez vos modèles avec du Deep Learning distribué
XebiCon'18 - Boostez vos modèles avec du Deep Learning distribuéPublicis Sapient Engineering
 
XebiCon'18 - Comment j'ai développé un jeu vidéo avec des outils de développe...
XebiCon'18 - Comment j'ai développé un jeu vidéo avec des outils de développe...XebiCon'18 - Comment j'ai développé un jeu vidéo avec des outils de développe...
XebiCon'18 - Comment j'ai développé un jeu vidéo avec des outils de développe...Publicis Sapient Engineering
 
XebiCon'18 - Les utilisateurs finaux, les oubliés de nos produits !
XebiCon'18 - Les utilisateurs finaux, les oubliés de nos produits !XebiCon'18 - Les utilisateurs finaux, les oubliés de nos produits !
XebiCon'18 - Les utilisateurs finaux, les oubliés de nos produits !Publicis Sapient Engineering
 
XebiCon'18 - Comment fausser l'interprétation de vos résultats avec des dataviz
XebiCon'18 - Comment fausser l'interprétation de vos résultats avec des datavizXebiCon'18 - Comment fausser l'interprétation de vos résultats avec des dataviz
XebiCon'18 - Comment fausser l'interprétation de vos résultats avec des datavizPublicis Sapient Engineering
 
XebiCon'18 - Architecturer son application mobile pour la durabilité
XebiCon'18 - Architecturer son application mobile pour la durabilitéXebiCon'18 - Architecturer son application mobile pour la durabilité
XebiCon'18 - Architecturer son application mobile pour la durabilitéPublicis Sapient Engineering
 
XebiCon'18 - Sécuriser son API avec OpenID Connect
XebiCon'18 - Sécuriser son API avec OpenID ConnectXebiCon'18 - Sécuriser son API avec OpenID Connect
XebiCon'18 - Sécuriser son API avec OpenID ConnectPublicis Sapient Engineering
 
XebiCon'18 - Structuration du Temps et Dynamique de Groupes, Théorie organisa...
XebiCon'18 - Structuration du Temps et Dynamique de Groupes, Théorie organisa...XebiCon'18 - Structuration du Temps et Dynamique de Groupes, Théorie organisa...
XebiCon'18 - Structuration du Temps et Dynamique de Groupes, Théorie organisa...Publicis Sapient Engineering
 
XebiCon'18 - La sécurité, douce illusion même en 2018
XebiCon'18 - La sécurité, douce illusion même en 2018XebiCon'18 - La sécurité, douce illusion même en 2018
XebiCon'18 - La sécurité, douce illusion même en 2018Publicis Sapient Engineering
 
XebiCon'18 - Utiliser Hyperledger Fabric pour la création d'une blockchain pr...
XebiCon'18 - Utiliser Hyperledger Fabric pour la création d'une blockchain pr...XebiCon'18 - Utiliser Hyperledger Fabric pour la création d'une blockchain pr...
XebiCon'18 - Utiliser Hyperledger Fabric pour la création d'une blockchain pr...Publicis Sapient Engineering
 
XebiCon'18 - Ce que l'histoire du métro Parisien m'a enseigné sur la création...
XebiCon'18 - Ce que l'histoire du métro Parisien m'a enseigné sur la création...XebiCon'18 - Ce que l'histoire du métro Parisien m'a enseigné sur la création...
XebiCon'18 - Ce que l'histoire du métro Parisien m'a enseigné sur la création...Publicis Sapient Engineering
 

Plus de Publicis Sapient Engineering (20)

XebiCon'18 - L'algorithme de reconnaissance de formes par le cerveau humain
XebiCon'18 - L'algorithme de reconnaissance de formes par le cerveau humainXebiCon'18 - L'algorithme de reconnaissance de formes par le cerveau humain
XebiCon'18 - L'algorithme de reconnaissance de formes par le cerveau humain
 
Xebicon'18 - IoT: From Edge to Cloud
Xebicon'18 - IoT: From Edge to CloudXebicon'18 - IoT: From Edge to Cloud
Xebicon'18 - IoT: From Edge to Cloud
 
Xebicon'18 - Spark in jail : conteneurisez vos traitements data sans serveur
Xebicon'18 - Spark in jail : conteneurisez vos traitements data sans serveurXebicon'18 - Spark in jail : conteneurisez vos traitements data sans serveur
Xebicon'18 - Spark in jail : conteneurisez vos traitements data sans serveur
 
XebiCon'18 - Modern Infrastructure
XebiCon'18 - Modern InfrastructureXebiCon'18 - Modern Infrastructure
XebiCon'18 - Modern Infrastructure
 
XebiCon'18 - La Web App d'aujourd'hui et de demain : état de l'art et bleedin...
XebiCon'18 - La Web App d'aujourd'hui et de demain : état de l'art et bleedin...XebiCon'18 - La Web App d'aujourd'hui et de demain : état de l'art et bleedin...
XebiCon'18 - La Web App d'aujourd'hui et de demain : état de l'art et bleedin...
 
XebiCon'18 - Des notebook pour le monitoring avec Zeppelin
XebiCon'18 - Des notebook pour le monitoring avec Zeppelin XebiCon'18 - Des notebook pour le monitoring avec Zeppelin
XebiCon'18 - Des notebook pour le monitoring avec Zeppelin
 
XebiCon'18 - Event Sourcing et RGPD, incompatibles ?
XebiCon'18 - Event Sourcing et RGPD, incompatibles ?XebiCon'18 - Event Sourcing et RGPD, incompatibles ?
XebiCon'18 - Event Sourcing et RGPD, incompatibles ?
 
XebiCon'18 - Deno, le nouveau NodeJS qui inverse la tendance ?
XebiCon'18 - Deno, le nouveau NodeJS qui inverse la tendance ?XebiCon'18 - Deno, le nouveau NodeJS qui inverse la tendance ?
XebiCon'18 - Deno, le nouveau NodeJS qui inverse la tendance ?
 
XebiCon'18 - Boostez vos modèles avec du Deep Learning distribué
XebiCon'18 - Boostez vos modèles avec du Deep Learning distribuéXebiCon'18 - Boostez vos modèles avec du Deep Learning distribué
XebiCon'18 - Boostez vos modèles avec du Deep Learning distribué
 
XebiCon'18 - Comment j'ai développé un jeu vidéo avec des outils de développe...
XebiCon'18 - Comment j'ai développé un jeu vidéo avec des outils de développe...XebiCon'18 - Comment j'ai développé un jeu vidéo avec des outils de développe...
XebiCon'18 - Comment j'ai développé un jeu vidéo avec des outils de développe...
 
XebiCon'18 - Les utilisateurs finaux, les oubliés de nos produits !
XebiCon'18 - Les utilisateurs finaux, les oubliés de nos produits !XebiCon'18 - Les utilisateurs finaux, les oubliés de nos produits !
XebiCon'18 - Les utilisateurs finaux, les oubliés de nos produits !
 
XebiCon'18 - Comment fausser l'interprétation de vos résultats avec des dataviz
XebiCon'18 - Comment fausser l'interprétation de vos résultats avec des datavizXebiCon'18 - Comment fausser l'interprétation de vos résultats avec des dataviz
XebiCon'18 - Comment fausser l'interprétation de vos résultats avec des dataviz
 
XebiCon'18 - Le développeur dans la Pop Culture
XebiCon'18 - Le développeur dans la Pop Culture XebiCon'18 - Le développeur dans la Pop Culture
XebiCon'18 - Le développeur dans la Pop Culture
 
XebiCon'18 - Architecturer son application mobile pour la durabilité
XebiCon'18 - Architecturer son application mobile pour la durabilitéXebiCon'18 - Architecturer son application mobile pour la durabilité
XebiCon'18 - Architecturer son application mobile pour la durabilité
 
XebiCon'18 - Sécuriser son API avec OpenID Connect
XebiCon'18 - Sécuriser son API avec OpenID ConnectXebiCon'18 - Sécuriser son API avec OpenID Connect
XebiCon'18 - Sécuriser son API avec OpenID Connect
 
XebiCon'18 - Structuration du Temps et Dynamique de Groupes, Théorie organisa...
XebiCon'18 - Structuration du Temps et Dynamique de Groupes, Théorie organisa...XebiCon'18 - Structuration du Temps et Dynamique de Groupes, Théorie organisa...
XebiCon'18 - Structuration du Temps et Dynamique de Groupes, Théorie organisa...
 
XebiCon'18 - Spark NLP, un an après
XebiCon'18 - Spark NLP, un an aprèsXebiCon'18 - Spark NLP, un an après
XebiCon'18 - Spark NLP, un an après
 
XebiCon'18 - La sécurité, douce illusion même en 2018
XebiCon'18 - La sécurité, douce illusion même en 2018XebiCon'18 - La sécurité, douce illusion même en 2018
XebiCon'18 - La sécurité, douce illusion même en 2018
 
XebiCon'18 - Utiliser Hyperledger Fabric pour la création d'une blockchain pr...
XebiCon'18 - Utiliser Hyperledger Fabric pour la création d'une blockchain pr...XebiCon'18 - Utiliser Hyperledger Fabric pour la création d'une blockchain pr...
XebiCon'18 - Utiliser Hyperledger Fabric pour la création d'une blockchain pr...
 
XebiCon'18 - Ce que l'histoire du métro Parisien m'a enseigné sur la création...
XebiCon'18 - Ce que l'histoire du métro Parisien m'a enseigné sur la création...XebiCon'18 - Ce que l'histoire du métro Parisien m'a enseigné sur la création...
XebiCon'18 - Ce que l'histoire du métro Parisien m'a enseigné sur la création...
 

XebiConFr 15 - Swift dans la vraie vie

  • 1. Swift dans la vraie vie
  • 2. #XebiConFr Swift dans la vraie vie Fabien Mirault Développeur Objective-C / Swift Speakers @viteinfinite Simone Civetta Développeur Objective-C / Swift @magici1
  • 4. #XebiConFr Swift dans la vraie vie Septembre 2014 Octobre 2014 Novembre 2014 Juin 2014 Apple annonce Swift ! Swift 1.0 ! Première application Swift Xebia sur l’App Store Swift 1.1 ? Janvier 2015 Nouvelles applications ? Swift ou pas ?
  • 6. #XebiConFr Swift dans la vraie vie Nouveau langage de développement Code plus lisible et moins verbeux Donc plus simple à maintenir ! Qu’est-ce que Swift ?
  • 7. #XebiConFr Swift dans la vraie vie Qu’est-ce que Swift ? Transition Objective-C → Swift aisée Moins de tolérance sur les erreurs de code Rapidité de développement accrue
  • 9. #XebiConFr Swift dans la vraie vie Septembre 2014 Octobre 2014 Novembre 2014 Juin 2014 Apple annonce Swift ! Swift 1.0 ! Première application Xebia sur l’App Store Swift 1.1 ? Janvier 2015 Nouvelles applications ! ! Swift ou pas ?
  • 10. Swift c’est cool……utilisé dans de vrais projets !
  • 11. #XebiConFr Swift dans la vraie vie TOC Nos cas d’usage Flux d’activité Création du projet et configuration Produits et synchronisation Langues Commentaires Testing Suivre son application Et l’Objective-C ?
  • 13. #XebiConFr Swift dans la vraie vie Création du projet Les dépendances Librairies dynamiques
  • 14. #XebiConFr Swift dans la vraie vie 14 Slide Title Title Au revoir iOS 7
  • 15. #XebiConFr Swift dans la vraie vie Création du projet Les dépendances
  • 17. #XebiConFr Swift dans la vraie vie Photos et vidéos Fluidité Des milliers de posts Flux d’activités
  • 18. #XebiConFr Swift dans la vraie vie Ne contient que ce qui a été défini Meilleures performances Stockage de type valeur et non référence Struct Flux d’activités
  • 19. #XebiConFr Swift dans la vraie vie Flux d’activités Exemple de Struct public struct Attachment { public let id: Int public let url: String public let type: String public let name: String public let objectId: Int public let mimeType: String public let objectType: String } Flux d’activités
  • 20. #XebiConFr Swift dans la vraie vie Struct : Performances Flux d’activités Avec une méthode de shuffle sur 1.000.000 d’objets Secondes 0 0,325 0,65 0,975 1,3 NSObject Struct 0,064 1,152
  • 21. #XebiConFr Swift dans la vraie vie Flux d’activités Struct VS Classes Ne peut pas hériter d’objets Pas de deinitializer Référence unique d’une instance
  • 22. #XebiConFr Swift dans la vraie vie Mapping automatique Génère des structs Performances accrues JSONJoy Flux d’activités
  • 23. #XebiConFr Swift dans la vraie vie Flux d’activités JSONJoy par l’exemple private static func buildUser(userData:[String: AnyObject]) -> User? { ... let user = User(JSONDecoder(userData)) return user }
  • 24. #XebiConFr Swift dans la vraie vie Flux d’activités Crash Flux d’activités
  • 25. #XebiConFr Swift dans la vraie vie Flux d’activités Struct Héritage Rendu Performances
  • 27. #XebiConFr Swift dans la vraie vie Analytics Endpoints Regroupement Profil Configurations
  • 28. #XebiConFr Swift dans la vraie vie Configurations struct Tags { struct Page { static let Login = "Login" static let Camera = "Camera" static let Newsfeed = "Newsfeed" static let Favorites = "Favorites" static let MyProfile = "MyProfile" static let OtherProfile = "OtherProfile" static let LiveSessions = "LiveSessions" static let CreateAccount = "CreateAccount" static let ForgottenPassword = "ForgottenPassword" } } Configurations
  • 30. #XebiConFr Swift dans la vraie vie Liste de produits 200.000+ lignes! Requêtes rapides!
  • 31. #XebiConFr Swift dans la vraie vie Liste de produits @implementation XBEntityStore - (void)addEntity:(id<XBEntity>)entity { // Some implementation } @end ... Un peu d’Objective-C - (void)addSomeObjects { XBEntityStore *productStore = [XBEntityStore new]; // XBProduct conforms to XBEntity XBProduct *product = [XBProduct new]; [productStore addEntity:product]; } Stockage : Objective-C
  • 32. #XebiConFr Swift dans la vraie vie - (void)addSomeObjects { XBEntityStore *productStore = [XBEntityStore new]; // XBProduct conforms to XBEntity XBProduct *product = [XBProduct new]; [productStore addEntity:product]; // XBColor conforms to XBEntity XBColor *color = [XBColor new]; [productStore addEntity:color]; } 32 Liste de produits Stockage : Objective-C @implementation XBEntityStore - (void)addEntity:(id<XBEntity>)entity { // Some implementation } @end ... Un peu d’Objective-C
  • 33. #XebiConFr Swift dans la vraie vie 33 Liste de produits Generics class EntityStore<T: Entity> { func addEntity(entity: T) { // Some implementation } } ... func addSomeObjects() { let productStore = EntityStore<Product>() // Product conforms to Entity let product = Product() productStore.addEntity(product) // Color conforms to Entity let color = Color() productStore.addEntity(color) } Un peu de Swift func addSomeObjects() { let productStore = EntityStore<Product>() // Product conforms to Entity let product = Product() productStore.addEntity(product) // Color conforms to Entity let color = Color() productStore.addEntity(color) // Ne compile pas ! }
  • 34. #XebiConFr Swift dans la vraie vie 34 Liste de produits Generics Écrire du code facilement réutilisable et sujet à des contraintes spécifiques
  • 35. #XebiConFr Swift dans la vraie vie 35 Liste de produits TypeAlias typealias ProductStore = EntityStore<Product> func addSomeObjects() { let productStore = ProductStore() // Product conforms to Entity let product = Product() productStore.addEntity(product) } typealias ColorStore = EntityStore<Color> func addSomeObjects() { let colorStore = ColorStore() // Color conforms to Entity let color = Color() colorStore.addEntity(product) } Code plus expressif
  • 36. #XebiConFr Swift dans la vraie vie 36 Liste de produits Protocols Swift est un “langage orienté protocoles” Apple, 2015 protocol Entity { } class EntityStore<T: Entity> { func addEntity(entity: T) { // Some implementation } }
  • 37. #XebiConFr Swift dans la vraie vie 37 Liste de produits Swift VS Swift class EntityStore { func addEntity(entity: Entity) { // Some implementation } } func addSomeObjects() { let productStore = EntityStore() let product = Product() productStore.addEntity(product) } Coder Swift != Penser Swift class EntityStore<T: Entity> { func addEntity(entity: T) { // Some implementation } } func addSomeObjects() { let productStore = ProductStore() let product = Product() productStore.addEntity(product) } Generics Typealias
  • 39. #XebiConFr Swift dans la vraie vie Synchronisation Synchronisation et manipulation* 500 Mo de données ! 200.000+ éléments! Performances!
  • 40. #XebiConFr Swift dans la vraie vie Synchronisation déclarations final et static Profiter pleinement du dispatch statique Performances
  • 41. #XebiConFr Swift dans la vraie vie Synchronisation Attention aux casts entre Array ↔ NSArray Dictionary ↔ NSDictionary Performances
  • 43. #XebiConFr Swift dans la vraie vie Librairie locale Appareil photo Ecran personnalisé Animation diaphragme Tâches asynchrones
  • 44. #XebiConFr Swift dans la vraie vie Tâches asynchrones Equivalent des blocks en Objective-C Comprend un bloc de code à exécuter Définition : {  ()  -­‐>  ()  in  } Closure
  • 45. #XebiConFr Swift dans la vraie vie Tâches asynchrones Exemple de closure self.closeDiaphragm(duration:0.3, completionBlock: { finished in self.openDiaphragm(duration:0.3) })
  • 46. #XebiConFr Swift dans la vraie vie Tâches asynchrones Optional Possède une valeur ou non Sécurise le code Tester la non nullité : if  let Définition : var  delegate:CameraDelegate?
  • 47. #XebiConFr Swift dans la vraie vie Tâches asynchrones Exemple d’optionals func setup(image:UIImage?) { if let menuIcon = image { let menuImageView = UIImageView(image: menuIcon) self.addSubview(menuImageView) } }
  • 48. #XebiConFr Swift dans la vraie vie 48 Tâches asynchrones Optionals : fiabilité !
  • 49. #XebiConFr Swift dans la vraie vie Appels asynchrones Poster un commentaire Sur n’importe quel post Gestion des retours serveur Tâches asynchrones
  • 50. #XebiConFr Swift dans la vraie vie Tâches asynchrones Promise Code plus lisible Idéal pour les tâches asynchrones Chaînage possible
  • 51. #XebiConFr Swift dans la vraie vie Tâches asynchrones Exemple de Promise // Parameters var parameters = Parameters() parameters["content"] = view.textView.text PostRequest.getHeaders() .success { token in return PostRequest.postContent(token, parameters) } .success { data in sendComplete() } .failure { (error, isCancelled) -> Void in sendFailed() }
  • 52. #XebiConFr Swift dans la vraie vie Tâches asynchrones Sans Promise // Parameters var parameters = Parameters() parameters["content"] = view.textView.text PostRequest.getHeaders() { [weak self] (token:String, error:NSError) -> Void in if token != nil { PostRequest.postContent(token, parameters) { [weak self] (result:Bool, error:NSError) -> Void in if result == true { if let strongSelf == self { strongSelf.sendComplete() } } else { if let strongSelf == self { strongSelf.sendFailed() } } } } else { if let strongSelf == self { strongSelf.sendFailed() } } }
  • 53. #XebiConFr Swift dans la vraie vie SwiftTasks Librairie principale Mise en place simple… …mais des erreurs dans Xcode
  • 54. #XebiConFr Swift dans la vraie vie Tâches asynchrones Erreurs avec Xcode if let colorsFilePath = syncDataConfiguration.colorsFile, data = NSData(contentsOfFile:colorsFilePath) { MetadataJSONDeserializer.deserialize(data, keyPath: "colors.color") .success { color -> ColorDuplicateRemovalTask in return self.removeDuplicateIdentifiers(colors) } .success { colors -> JSONInsertTask in return entityStore.replaceAllObjects(colors, transformer: Color.tranform) } .success { JSONs -> Void in taskTuple.fulfill(JSONs) } .failure { (error, isCancelled) in if let error = error { taskTuple.reject(error) } } return taskTuple.task }
  • 56. #XebiConFr Swift dans la vraie vie Disponibilité produit Simple requête HTTP! Mise à jour de la UI!
  • 57. #XebiConFr Swift dans la vraie vie Disponibilité produit Alamofire Alamofire.request(URLRequest) .validate() .response { (request, response, data, error) in print(request) print(response) print(data) print(error) }
  • 58. #XebiConFr Swift dans la vraie vie Disponibilité produit Les étapes WebService Déserialisation UI
  • 59. #XebiConFr Swift dans la vraie vie 59 Disponibilité produit Functional Reactive Programming Propagation des changements Flux de données Asynchronisme
  • 60. #XebiConFr Swift dans la vraie vie ReactiveCocoa Reactive Cocoa Disponibilité produit
  • 61. #XebiConFr Swift dans la vraie vie ReactKit github.com/ReactKit/ Disponibilité produit
  • 62. #XebiConFr Swift dans la vraie vie Disponibilité produit Functional Reactive Programming ^{ let available = $0 as! Bool self.availabilitySpinner.stopAnimating() self.availabilityIndicator.textColor = self.colorForStatus(available) } <~ KVO.signal(viewModel, "status")
  • 63. #XebiConFr Swift dans la vraie vie [[[RACObserve(viewModel.status) map:^id(NSString *status) { if ([status isKindOfClass:[NSString class]]) { return status; } return nil; }] map:^id(NSString *status) { return @([status isEqualToString:@“available"]); }] delay:1.0]; [[[RACObserve(viewModel.status) map:^id(NSString *status) { if ([status isKindOfClass:[NSString class]]) { return status; } return nil; }] map:^id(NSString *status) { return @([status isEqualToString:@“available"]); }] delay:1.0]; Disponibilité produit FRP - Objective-C
  • 64. #XebiConFr Swift dans la vraie vie Disponibilité produit FRP - Swift let availabilitySignal = KVO.signal(viewModel, "status") .map { status -> String? in return status as? String } .map { status -> Bool in return status == "available" } .delay(1.0)
  • 65. #XebiConFr Swift dans la vraie vie Disponibilité produit Opérateurs Custom ^{ self.availabilitySpinner.stopAnimating() self.availabilityIndicator.textColor = self.colorForStatus($0) } <~ availabilitySignal<~
  • 66. #XebiConFr Swift dans la vraie vie Slide Title Title
  • 68. #XebiConFr Swift dans la vraie vie Internationalisation Changement de la langue! Traduction des contenus! Traduction de l’IHM!
  • 69. #XebiConFr Swift dans la vraie vie Internationalisation self.headerLabel.text = NSLocalizedString("Header.Title", comment: "Header Title") extension UILabel { var localizedText: String { set { self.text = NSLocalizedString(newValue, comment: newValue) } /* ... */ } } self.headerLabel.localizedText = "Header.Title" Extensions
  • 70. #XebiConFr Swift dans la vraie vie 70 Internationalisation Enums typedef enum : NSUInteger { XBCountryUSA, XBCountryChina, XBCountryItaly } XBCountry; Un peu d’Objective-C
  • 71. #XebiConFr Swift dans la vraie vie 71 Internationalisation Enums enum Country: String { case USA = "US" case China = "CN" case Italy = "IT" } Et finalement du Swift Valeurs associées
  • 72. #XebiConFr Swift dans la vraie vie 72 Internationalisation Enums enum Country: String { case USA = "US" case China = "CN" case Italy = "IT" static var defaultCountry: Country { return Country.Italy } } Country.defaultCountry Et finalement du Swift Valeurs associées Propriétés
  • 73. #XebiConFr Swift dans la vraie vie 73 Internationalisation Switch enum Language { case English(region: String) case Italian var name: String { switch self { case .English(let region): return "English " + region case .Italian: return "Italian" } } } Swift
  • 74. #XebiConFr Swift dans la vraie vie 74 Internationalisation Switch enum Language { case English(region: String) case Italian var name: String { switch self { case .English(let region): return "English " + region case .Italian: return "Italian" } } } Swift Pattern matching
  • 75. #XebiConFr Swift dans la vraie vie enum Language { case English(region: String) case Italian var name: String { switch self { case .English(let region) where region == "US": return "English Default” case .English(let region): return "English " + region case .Italian: return "Italian" } } 75 Internationalisation Switch Swift Pattern matching Switch exhaustif
  • 76. #XebiConFr Swift dans la vraie vie Internationalisation Enums : it’s over 9000!! First-Class citizens Méthodes et propriétés Valeurs associées
  • 77. Tests
  • 78. #XebiConFr Swift dans la vraie vie Tests Assurer le fonctionnement de l’application Se protéger des régressions
  • 79. #XebiConFr Swift dans la vraie vie Tests Stockage des produits static func processProducts(products: [Product]) { products.filter { ... } Stores.ProductStore.insertObjects(products) } ... processProducts(myProducts) func testProcessProducts() { // Setup let products = [Product("A"), Product("B")] let productManager = ProductManager() // Run productManager.processProducts(products) // Verify // ?? } Comment tester ?
  • 80. #XebiConFr Swift dans la vraie vie 80 Tests Stockage des produits func testProcessProducts() { // Setup let products = [Product("A"), Product("B")] let mockProductStore = ProductStore(coordinator: MockCoordinator()) let productManager = ProductManager() // Run productManager.processProducts(products, productStore: mockProductStore) // Verify XCTAssertEqual(productStore.allObjects().count, 2) } func processProducts(products: [Product], productStore: ProductStore = ProductStore()) { products.filter { ... } productStore.insertObjects(products) } ... processProducts(myProducts)
  • 81. #XebiConFr Swift dans la vraie vie 81 Slide Title Title
  • 82. #XebiConFr Swift dans la vraie vie 82 Tests Mais aussi…
  • 83. #XebiConFr Swift dans la vraie vie 83 Tests Mais aussi…
  • 84. #XebiConFr Swift dans la vraie vie 84 Tests Mais aussi…
  • 86. #XebiConFr Swift dans la vraie vie Suivre son application Déploiement centralisé et versionné Remontées de crashs Statistiques d’utilisation Fabric
  • 87. #XebiConFr Swift dans la vraie vie Suivre son application Fabric - Objective-C RTSViewController.m line 1310 -[RTSViewController getCurrentUDPValues] Fatal Exception: NSRangeException *** -[__NSArrayM objectAtIndex:] index 4294967292 beyond bounds [0 .. 511]
  • 88. #XebiConFr Swift dans la vraie vie Suivre son application Fabric - Swift WSClient.swift line 31 static MyLittlePony.WSClient.requestContent (MyLittlePony.WSClient.Type) parameters : Swift.Optional <Swift.Dictionary <Swift.String, Swift.AnyObject> Crashed: com.apple.main-thread SIGABRT ABORT at 0x312a8df0
  • 89. #XebiConFr Swift dans la vraie vie Suivre son application Reveal Vue éclatée Fonctionne sur simulateur ou device Édition à la volée des propriétés
  • 90. #XebiConFr Swift dans la vraie vie Suivre son application Reveal
  • 91. #XebiConFr Swift dans la vraie vie Suivre son application Suivre son application Évolution du langage constante Rétrocompatibilité non assurée
  • 93. #XebiConFr Swift dans la vraie vie Toujours valable Mais développement plus lent Migration progressive conseillée Et l’Objective-C dans tout ça ?
  • 94. #XebiConFr Swift dans la vraie vie Popularitédesrecherches 2014 2015 Objective-C Swift Objective-C Swift Source : TIOBE 3 ème 19 ème 14 ème 15 ème Et l’Objective-C dans tout ça ?
  • 95. #XebiConFr Swift dans la vraie vieNouveaux Repositories entre Q3 et Q4 2014 Swift Objective-C 97 3757 Source : http://githut.info Et l’Objective-C dans tout ça ?
  • 96. #XebiConFr Swift dans la vraie vie Les avantages de Swift Plus facile à maintenir et plus robuste Demande moins de code Soyez acteur des évolutions d’Apple !
  • 98. #XebiConFr Swift dans la vraie vie Un peu de lecture A Swift Kickstart
 Daniel Steinberg Functional Programming in Swift
 Chris Eidhof, Florian Kugler, and Wouter Swierstra http://blog.xebia.fr/tag/swift L’équipe iOS Xebia Advanced Swift
 Chris Eidhof and Airspeed Velocity