Slide 1

Slide 1 text

Let me write your networking code Nicola Corti @cortinico

Slide 2

Slide 2 text

YELP CORP DECK Footnote should go here

Slide 3

Slide 3 text

LET ME WRITE YOUR NETWORKING CODE Nicola Corti Android Infra Engineer @cortinico Community Lover
 (GDG Pisa - Kotlin Hamburg) ! ✈

Slide 4

Slide 4 text

No content

Slide 5

Slide 5 text

Photo by Brianna Santellan on Unsplash

Slide 6

Slide 6 text

GET Photo by Brianna Santellan on Unsplash

Slide 7

Slide 7 text

GET-/pet/corgi Photo by Brianna Santellan on Unsplash

Slide 8

Slide 8 text

No content

Slide 9

Slide 9 text

Photo by Hannah Lim on Unsplash

Slide 10

Slide 10 text

petstore.swagger.io You can’t just GET-/pet/corgi Photo by Hannah Lim on Unsplash

Slide 11

Slide 11 text

Swagger & Open API

Slide 12

Slide 12 text

Open API The Specification Swagger The Tooling Define the API in a JSON/YAML files Build infrastructure around them SWAGGER Swagger & Open API

Slide 13

Slide 13 text

No content

Slide 14

Slide 14 text

!!--- swagger: '2.0'

Slide 15

Slide 15 text

!!--- swagger: '2.0' info:

Slide 16

Slide 16 text

!!--- swagger: '2.0' info: description: 'This is a sample server Petstore server'

Slide 17

Slide 17 text

!!--- swagger: '2.0' info: description: 'This is a sample server Petstore server' version: 1.0.0

Slide 18

Slide 18 text

!!--- swagger: '2.0' info: description: 'This is a sample server Petstore server' version: 1.0.0 title: Swagger Petstore

Slide 19

Slide 19 text

!!--- swagger: '2.0' info: description: 'This is a sample server Petstore server' version: 1.0.0 title: Swagger Petstore contact: email: [email protected]

Slide 20

Slide 20 text

!!--- swagger: '2.0' info: description: 'This is a sample server Petstore server' version: 1.0.0 title: Swagger Petstore contact: email: [email protected] license: name: Apache 2.0 url: http:!//!!www.apache.org/licenses/LICENSE-2.0.html

Slide 21

Slide 21 text

!!--- swagger: '2.0' info: description: 'This is a sample server Petstore server' version: 1.0.0 title: Swagger Petstore contact: email: [email protected] license: name: Apache 2.0 url: http:!//!!www.apache.org/licenses/LICENSE-2.0.html host: petstore.swagger.io

Slide 22

Slide 22 text

!!--- swagger: '2.0' info: description: 'This is a sample server Petstore server' version: 1.0.0 title: Swagger Petstore contact: email: [email protected] license: name: Apache 2.0 url: http:!//!!www.apache.org/licenses/LICENSE-2.0.html host: petstore.swagger.io basePath: "/v2"

Slide 23

Slide 23 text

!!--- swagger: '2.0' info: description: 'This is a sample server Petstore server' version: 1.0.0 title: Swagger Petstore contact: email: [email protected] license: name: Apache 2.0 url: http:!//!!www.apache.org/licenses/LICENSE-2.0.html host: petstore.swagger.io basePath: "/v2" schemes: - https - http

Slide 24

Slide 24 text

basePath: “/v2" schemes: - https - http definitions:

Slide 25

Slide 25 text

basePath: “/v2" schemes: - https - http definitions: Pet:

Slide 26

Slide 26 text

basePath: “/v2" schemes: - https - http definitions: Pet: type: object

Slide 27

Slide 27 text

basePath: “/v2" schemes: - https - http definitions: Pet: type: object properties: 


Slide 28

Slide 28 text

basePath: “/v2" schemes: - https - http definitions: Pet: type: object properties: id: type: integer format: int64


Slide 29

Slide 29 text

basePath: “/v2" schemes: - https - http definitions: Pet: type: object properties: id: type: integer format: int64 name: type: string

Slide 30

Slide 30 text

basePath: “/v2" schemes: - https - http definitions: Pet: type: object properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string

Slide 31

Slide 31 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string 


Slide 32

Slide 32 text

properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string 


Slide 33

Slide 33 text

properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string description: pet status in the store 


Slide 34

Slide 34 text

properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string description: pet status in the store enum: - available - sold 


Slide 35

Slide 35 text

properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string description: pet status in the store enum: - available - sold category: 


Slide 36

Slide 36 text

properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string description: pet status in the store enum: - available - sold category: $ref: “#/definitions/Category"

Slide 37

Slide 37 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string description: pet status in the store enum: - available - sold category: $ref: “#/definitions/Category" 


Slide 38

Slide 38 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string description: pet status in the store enum: - available - sold category: $ref: “#/definitions/Category" 
 Category:

Slide 39

Slide 39 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string description: pet status in the store enum: - available - sold category: $ref: “#/definitions/Category" 
 Category: type: object

Slide 40

Slide 40 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string description: pet status in the store enum: - available - sold category: $ref: “#/definitions/Category" 
 Category: type: object properties: id: type: integer format: int64

Slide 41

Slide 41 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string description: pet status in the store enum: - available - sold category: $ref: “#/definitions/Category" 
 Category: type: object properties: id: type: integer format: int64 name: type: string

Slide 42

Slide 42 text

No content

Slide 43

Slide 43 text

paths:

Slide 44

Slide 44 text

paths: /pet/{petId}:

Slide 45

Slide 45 text

paths: /pet/{petId}: get:

Slide 46

Slide 46 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet

Slide 47

Slide 47 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById

Slide 48

Slide 48 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json

Slide 49

Slide 49 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters:

Slide 50

Slide 50 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId

Slide 51

Slide 51 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path

Slide 52

Slide 52 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return

Slide 53

Slide 53 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return required: true

Slide 54

Slide 54 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return required: true type: integer

Slide 55

Slide 55 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return required: true type: integer format: int64

Slide 56

Slide 56 text

- name: petId in: path description: ID of pet to return required: true type: integer format: int64

Slide 57

Slide 57 text

- name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses:

Slide 58

Slide 58 text

- name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200':

Slide 59

Slide 59 text

- name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation

Slide 60

Slide 60 text

- name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation '404':

Slide 61

Slide 61 text

- name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation '404': description: Pet not found

Slide 62

Slide 62 text

- name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation schema: $ref: "" '404': description: Pet not found

Slide 63

Slide 63 text

- name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation schema: $ref: "#/definitions/Pet" '404': description: Pet not found

Slide 64

Slide 64 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation schema: $ref: "#/definitions/Pet" '404': description: Pet not found

Slide 65

Slide 65 text

SWAGGER UI

Slide 66

Slide 66 text

SWAGGER EDITOR

Slide 67

Slide 67 text

GET-/pet/corgi Photo by Brianna Santellan on Unsplash

Slide 68

Slide 68 text

GET-/pet/42 Photo by Brianna Santellan on Unsplash

Slide 69

Slide 69 text

No content

Slide 70

Slide 70 text

No content

Slide 71

Slide 71 text

public Pet getPet(final String id) { String https_url = "https:!//petstore.swagger.io/v2/pet/" + id; URL url; try { url = new URL(https_url); HttpsURLConnection con = (HttpsURLConnection) url.openConnection(); if (con !!= null) { BufferedReader br = new BufferedReader(new InputStreamReader(con.getInputStream())); String response = ""; String input; while ((input = br.readLine()) !!= null) { System.out.println(input); response += input; } br.close(); JSONObject object = new JSONObject(response); Pet result = new Pet(); result.setId(object.getInt("id")); result.setName(object.getString("name")); result.setStatus(object.getString("status")); JSONArray photos = object.getJSONArray("photoUrls"); List photoArrays = new ArrayList!<>(); for (int i = 0; i < photos.length(); i!++) { photoArrays.add(photos.getString(i)); } result.setPhotoUrls(photoArrays); JSONArray tags = object.getJSONArray("tags"); List tagArrays = new ArrayList!<>(); for (int i = 0; i < tags.length(); i!++) { tagArrays.add(tags.getString(i)); } result.setTags(tagArrays); System.out.println(result); System.out.println(result.getId()); System.out.println(result.getName()); System.out.println(result.getPhotoUrls().get(0)); System.out.println(result.getStatus()); System.out.println(result.getTags().get(0)); return result; } } catch (MalformedURLException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } catch (JSONException e) { e.printStackTrace(); } return null; } public class Pet { private Integer id; private String name; private List photoUrls = null; private List tags = null; private String status; public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public List getPhotoUrls() { return photoUrls; } public void setPhotoUrls(List photoUrls) { this.photoUrls = photoUrls; } public List getTags() { return tags; } public void setTags(List tags) { this.tags = tags; } public String getStatus() { return status; } public void setStatus(String status) { this.status = status; } } fun getPet(id: String): Pet? { val https_url = "https:!//petstore.swagger.io/v2/pet/$id" val url: URL try { url = URL(https_url) val con = url.openConnection() as HttpsURLConnection val br = BufferedReader(InputStreamReader(con.inputStream)) var response = "" var input: String? = br.readLine() while (input !!= null) { println(input) response += input input = br.readLine() } br.close() val parsedObject = JSONObject(response) val photos = parsedObject.getJSONArray("photoUrls") val photoArrays = ArrayList() for (i in 0 until photos.length()) { photoArrays.add(photos.getString(i)) } val tags = parsedObject.getJSONArray("tags") val tagArrays = ArrayList() for (i in 0 until tags.length()) { tagArrays.add(tags.getString(i)) } val result = Pet( id = parsedObject.getInt("id"), name = parsedObject.getString("name"), status = parsedObject.getString("status"), photoUrls = photoArrays, tags = tagArrays ) println(result) println(result.id) println(result.name) println(result.photoUrls!!![0]) println(result.status) println(result.tags!!![0]) return result } catch (e: MalformedURLException) { e.printStackTrace() } catch (e: IOException) { e.printStackTrace() } catch (e: JSONException) { e.printStackTrace() } return null } data class Pet( var id: Int?, var name: String?, var photoUrls: List?, var tags: List?, var status: String? ) data class Tag(var id: Int?, var name: String?) fun getPet(id: String): Pet? { val https_url = "https:!//petstore.swagger.io/v2/pet/$id" val url: URL try { url = URL(https_url) val con = url.openConnection() as HttpsURLConnection val br = BufferedReader(InputStreamReader(con.inputStream)) var response = "" var input: String? = br.readLine() while (input !!= null) { println(input) response += input input = br.readLine() } br.close() val moshi = Moshi.Builder().build() val jsonAdapter = moshi.adapter(Pet!::class.java) val pet = jsonAdapter.fromJson(response) println(pet) return pet } catch (e: MalformedURLException) { e.printStackTrace() } catch (e: IOException) { e.printStackTrace() } return null } data class Pet( var id: Int?, var name: String?, var photoUrls: List?, var tags: List?, var status: String? ) data class Tag(var id: Int?, var name: String?) fun getPet(id: String): Pet? { val client = OkHttpClient.Builder().build() val request = Request.Builder().url("https:!//petstore.swagger.io/v2/pet/$id").build() client.newCall(request).execute().use { val moshi = Moshi.Builder().build() val jsonAdapter = moshi.adapter(Pet!::class.java) val pet = jsonAdapter.fromJson(it.body()!?.string()!!!) println(pet) return pet } } data class Pet( var id: Int?, var name: String?, var photoUrls: List?, var tags: List?, var status: String? ) data class Tag(var id: Int?, var name: String?)

Slide 72

Slide 72 text

r.io/v2/pet/$id" tpsURLConnection eader(con.inputStream)) (Pet!::class.java) nse) g?) fun getPet(id: String): Pet? { val client = OkHttpClient.Builder().build() val request = Request.Builder().url("https:!//petstore.swagger.io/v2/pet/$id").build() client.newCall(request).execute().use { val moshi = Moshi.Builder().build() val jsonAdapter = moshi.adapter(Pet!::class.java) val pet = jsonAdapter.fromJson(it.body()!?.string()!!!) println(pet) return pet } } data class Pet( var id: Int?, var name: String?, var photoUrls: List?, var tags: List?, var status: String? ) data class Tag(var id: Int?, var name: String?)

Slide 73

Slide 73 text

r.io/v2/pet/$id" tpsURLConnection eader(con.inputStream)) (Pet!::class.java) nse) g?) fun getPet(id: String): Pet? { val client = OkHttpClient.Builder().build() val request = Request.Builder().url("https:!//petstore.swagger.io/v2/pet/$id").build() client.newCall(request).execute().use { val moshi = Moshi.Builder().build() val jsonAdapter = moshi.adapter(Pet!::class.java) val pet = jsonAdapter.fromJson(it.body()!?.string()!!!) println(pet) return pet } } data class Pet( var id: Int?, var name: String?, var photoUrls: List?, var tags: List?, var status: String? ) data class Tag(var id: Int?, var name: String?) interface PetInterface { @GET("pet/{id}") fun getPet(@Path("id") id: String?) : Call } .getPet(“42")

Slide 74

Slide 74 text

Swagger Codegen

Slide 75

Slide 75 text

SWAGGER CODEGEN

Slide 76

Slide 76 text

On Github: swagger-api/swagger-codegen Generator & Templates Several templates already available Command line tool SWAGGER CODEGEN Swagger Codegen java -jar swagger-codegen-cli-2.3.1.jar generate \ -i swagger.yaml \ --api-package com.yelp.codegen.sample.api \ --model-package com.yelp.codegen.sample.model \ --group-id com.yelp.codegen.sample \ --artifact-id sample-codegen \ --artifact-version 0.0.1 \ -l spring \ -o sample-codegen

Slide 77

Slide 77 text

{{#model}}{{#description}} /** * {{description}} **/{{/description}} @ApiModel(description = "{{{description}}}") public class {{classname}} {{#parent}}extends {{{parent}}}{{/parent}} { {{#vars}}{{#isEnum}} public enum {{datatypeWithEnum}} { {{#allowableValues}}{{#values}} {{•}}, {{/values}}{{/allowableValues}} }; @SerializedName("{{baseName}}") private {{{datatypeWithEnum}}} {{name}} = {{{defaultValue}}};{{/isEnum}}{{^isEnum}} @SerializedName("{{baseName}}") private {{{datatype}}} {{name}} = {{{defaultValue}}};{{/isEnum}}{{/vars}} {{#vars}} /**{{#description}} * {{{description}}}{{/description}}{{#minimum}} * minimum: {{minimum}}{{/minimum}}{{#maximum}} * maximum: {{maximum}}{{/maximum}} **/ @ApiModelProperty({{#required}}required = {{required}}, {{/required}}value = "{{{description}}}") public {{{datatypeWithEnum}}} {{getter}}() { return {{name}}; } public void {{setter}}({{{datatypeWithEnum}}} {{name}}) { this.{{name}} = {{name}}; }

Slide 78

Slide 78 text

{{#model}}{{#description}} /** * {{description}} **/{{/description}} @ApiModel(description = "{{{description}}}") public class {{classname}} {{#parent}}extends {{{p {{#vars}}{{#isEnum}} public enum {{datatypeWithEnum}} { {{#allowableValues}}{{#values}} {{•}}, {{/valu }; @SerializedName("{{baseName}}") private {{{datatypeWithEnum}}} {{name}} = {{{def

Slide 79

Slide 79 text

{{#model}}{{#description}} /** * {{description}} **/{{/description}} @ApiModel(description = "{{{description}}}") public class {{classname}} {{#parent}}extends {{{p {{#vars}}{{#isEnum}} public enum {{datatypeWithEnum}} { {{#allowableValues}}{{#values}} {{•}}, {{/valu }; @SerializedName("{{baseName}}") private {{{datatypeWithEnum}}} {{name}} = {{{def

Slide 80

Slide 80 text

Swagger Gradle
 Codegen

Slide 81

Slide 81 text

SWAGGER GRADLE CODEGEN

Slide 82

Slide 82 text

Plug it inside your gradle build Input/Output aware Simpler API for the developer SWAGGER GRADLE CODEGEN Yelp/swagger-gradle-codegen A Gradle Plugin

Slide 83

Slide 83 text

SWAGGER GRADLE CODEGEN Yelp/swagger-gradle-codegen Opinionated ✓ Kotlin ✓ RxJava2 ✓ Retrofit ✓ Moshi ✓ ThreeTenABP

Slide 84

Slide 84 text

No content

Slide 85

Slide 85 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string description: pet status in the store enum: - available - sold category: $ref: “#/definitions/Category" 
 Category: type: object properties: id: type: integer format: int64 name: type: string

Slide 86

Slide 86 text

Category: type: object properties: id: type: integer format: int64 name: type: string

Slide 87

Slide 87 text

Category: type: object properties: id: type: integer format: int64 name: type: string class Category()

Slide 88

Slide 88 text

Category: type: object properties: id: type: integer format: int64 name: type: string data class Category()

Slide 89

Slide 89 text

Category: type: object properties: id: type: integer format: int64 name: type: string data class Category( var id, var name )

Slide 90

Slide 90 text

Category: type: object properties: id: type: integer format: int64 name: type: string data class Category( var id: Long, var name: String )

Slide 91

Slide 91 text

Category: type: object properties: id: type: integer format: int64 name: type: string data class Category( var id: Long?, var name: String? )

Slide 92

Slide 92 text

Category: type: object properties: id: type: integer format: int64 name: type: string data class Category( var id: Long? = null, var name: String? = null )

Slide 93

Slide 93 text

Category: type: object properties: id: type: integer format: int64 name: type: string data class Category( @Json(name = "id") var id: Long? = null, @Json(name = "name") var name: String? = null )

Slide 94

Slide 94 text

Category: type: object properties: id: type: integer format: int64 name: type: string import com.squareup.moshi.Json data class Category( @Json(name = "id") var id: Long? = null, @Json(name = "name") var name: String? = null )

Slide 95

Slide 95 text

Category: type: object description: properties: id: type: integer description: format: int64 name: type: string description: import com.squareup.moshi.Json data class Category( @Json(name = "id") var id: Long? = null, @Json(name = "name") var name: String? = null )

Slide 96

Slide 96 text

Category: type: object description: A Category used to group pets properties: id: type: integer description: Unique ID of the Category format: int64 name: type: string description: Name of this category import com.squareup.moshi.Json data class Category( @Json(name = "id") var id: Long? = null, @Json(name = "name") var name: String? = null )

Slide 97

Slide 97 text

Category: type: object description: A Category used to group pets properties: id: type: integer description: Unique ID of the Category format: int64 name: type: string description: Name of this category import com.squareup.moshi.Json /** * A Category used to group pets * @property id Unique ID of the Category * @property name Name of this category */ data class Category( @Json(name = "id") var id: Long? = null, @Json(name = "name") var name: String? = null )

Slide 98

Slide 98 text

No content

Slide 99

Slide 99 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string enum: - available - sold category: $ref: “#/definitions/Category" 


Slide 100

Slide 100 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string enum: - available - sold category: $ref: “#/definitions/Category" 
 package com.yelp.codegen.samples.models import com.squareup.moshi.Json data class Pet ( @Json(name = "name") var name: String, @Json(name = "photoUrls") var photoUrls: List, @Json(name = "category") var category: Category? = null, @Json(name = "id") var id: Long? = null, @Json(name = "status") var status: Pet.StatusEnum? = null ) { enum class StatusEnum(val value: String){ @Json(name = "available") AVAILABLE("available"), @Json(name = "sold") SOLD("sold") } }

Slide 101

Slide 101 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string enum: - available - sold category: $ref: “#/definitions/Category" 
 package com.yelp.codegen.samples.models import com.squareup.moshi.Json data class Pet ( @Json(name = "name") var name: String, @Json(name = "photoUrls") var photoUrls: List, @Json(name = "category") var category: Category? = null, @Json(name = "id") var id: Long? = null, @Json(name = "status") var status: Pet.StatusEnum? = null ) { enum class StatusEnum(val value: String){ @Json(name = "available") AVAILABLE("available"), @Json(name = "sold") SOLD("sold") } }

Slide 102

Slide 102 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string enum: - available - sold category: $ref: “#/definitions/Category" 
 package com.yelp.codegen.samples.models import com.squareup.moshi.Json data class Pet ( @Json(name = "name") var name: String, @Json(name = "photoUrls") var photoUrls: List, @Json(name = "category") var category: Category? = null, @Json(name = "id") var id: Long? = null, @Json(name = "status") var status: Pet.StatusEnum? = null ) { enum class StatusEnum(val value: String){ @Json(name = "available") AVAILABLE("available"), @Json(name = "sold") SOLD("sold") } }

Slide 103

Slide 103 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string enum: - available - sold category: $ref: “#/definitions/Category" 
 package com.yelp.codegen.samples.models import com.squareup.moshi.Json data class Pet ( @Json(name = "name") var name: String, @Json(name = "photoUrls") var photoUrls: List, @Json(name = "category") var category: Category? = null, @Json(name = "id") var id: Long? = null, @Json(name = "status") var status: Pet.StatusEnum? = null ) { enum class StatusEnum(val value: String){ @Json(name = "available") AVAILABLE("available"), @Json(name = "sold") SOLD("sold") } }

Slide 104

Slide 104 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string enum: - available - sold category: $ref: “#/definitions/Category" 
 package com.yelp.codegen.samples.models import com.squareup.moshi.Json data class Pet ( @Json(name = "name") var name: String, @Json(name = "photoUrls") var photoUrls: List, @Json(name = "category") var category: Category? = null, @Json(name = "id") var id: Long? = null, @Json(name = "status") var status: Pet.StatusEnum? = null ) { enum class StatusEnum(val value: String){ @Json(name = "available") AVAILABLE("available"), @Json(name = "sold") SOLD("sold") } }

Slide 105

Slide 105 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string enum: - available - sold category: $ref: “#/definitions/Category" 
 package com.yelp.codegen.samples.models import com.squareup.moshi.Json data class Pet ( @Json(name = "name") var name: String, @Json(name = "photoUrls") var photoUrls: List, @Json(name = "category") var category: Category? = null, @Json(name = "id") var id: Long? = null, @Json(name = "status") var status: Pet.StatusEnum? = null ) { enum class StatusEnum(val value: String){ @Json(name = "available") AVAILABLE("available"), @Json(name = "sold") SOLD("sold") } }

Slide 106

Slide 106 text

definitions: Pet: type: object required: - name - photoUrls properties: id: type: integer format: int64 name: type: string photoUrls: type: array items: type: string status: type: string enum: - available - sold category: $ref: “#/definitions/Category" 
 package com.yelp.codegen.samples.models import com.squareup.moshi.Json /** * Represents a specific Pet in the store * @property category Optional category of the pet * @property id Unique ID of this Pet * @property name Name of this specific pet * @property photoUrls Photo URLs for this Pet on the bucket * @property status Pet status in the store */ data class Pet ( @Json(name = "name") var name: String, @Json(name = "photoUrls") var photoUrls: List, @Json(name = "category") var category: Category? = null, @Json(name = "id") var id: Long? = null, @Json(name = "status") var status: Pet.StatusEnum? = null ) { /** * Pet status in the store * Values: AVAILABLE, SOLD */ enum class StatusEnum(val value: String){ @Json(name = "available") AVAILABLE("available"), @Json(name = "sold") SOLD("sold") } }

Slide 107

Slide 107 text

No content

Slide 108

Slide 108 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation schema: $ref: "#/definitions/Pet" '404': description: Pet not found

Slide 109

Slide 109 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation schema: $ref: "#/definitions/Pet" '404': description: Pet not found interface DefaultApi { }

Slide 110

Slide 110 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation schema: $ref: "#/definitions/Pet" '404': description: Pet not found interface DefaultApi { fun getPetById() }

Slide 111

Slide 111 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation schema: $ref: "#/definitions/Pet" '404': description: Pet not found interface DefaultApi { fun getPetById( @retrofit2.http.Path("petId") petId: Long ) }

Slide 112

Slide 112 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation schema: $ref: "#/definitions/Pet" '404': description: Pet not found interface DefaultApi { @GET("/pet/{petId}") fun getPetById( @retrofit2.http.Path("petId") petId: Long ) }

Slide 113

Slide 113 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation schema: $ref: "#/definitions/Pet" '404': description: Pet not found interface DefaultApi { @GET("/pet/{petId}") fun getPetById( @retrofit2.http.Path("petId") petId: Long ): Single }

Slide 114

Slide 114 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation schema: $ref: "#/definitions/Pet" '404': description: Pet not found interface DefaultApi { @Headers( "X-Operation-ID: getPetById" ) @GET("/pet/{petId}") fun getPetById( @retrofit2.http.Path("petId") petId: Long ): Single }

Slide 115

Slide 115 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation schema: $ref: "#/definitions/Pet" '404': description: Pet not found interface DefaultApi { /** * Find pet by ID * Returns a single pet * @param petId ID of pet to return (required) */ @Headers( "X-Operation-ID: getPetById" ) @GET("/pet/{petId}") fun getPetById( @retrofit2.http.Path("petId") petId: Long ): Single }

Slide 116

Slide 116 text

paths: /pet/{petId}: get: summary: Find pet by ID description: Returns a single pet operationId: getPetById produces: - application/json parameters: - name: petId in: path description: ID of pet to return required: true type: integer format: int64 responses: '200': description: successful operation schema: $ref: "#/definitions/Pet" '404': description: Pet not found package com.yelp.codegen.generatecodesamples.apis import com.yelp.codegen.generatecodesamples.models.Pet import io.reactivex.Single import retrofit2.http.GET import retrofit2.http.Headers interface DefaultApi { /** * Find pet by ID * Returns a single pet * @param petId ID of pet to return (required) */ @Headers( "X-Operation-ID: getPetById" ) @GET("/pet/{petId}") fun getPetById( @retrofit2.http.Path("petId") petId: Long ): Single }

Slide 117

Slide 117 text

Build an app module with specs locally Build a pure-Kotlin module with a specs locally Build a library project that contains your models/apis Integrate your library with your CI system SWAGGER GRADLE CODEGEN Yelp/swagger-gradle-codegen Use cases

Slide 118

Slide 118 text

No content

Slide 119

Slide 119 text

buildscript { repositories { gradlePluginPortal() } dependencies { classpath "com.yelp.codegen:plugin:1.0.0" } }

Slide 120

Slide 120 text

buildscript { repositories { gradlePluginPortal() } dependencies { classpath "com.yelp.codegen:plugin:1.0.0" } } generateSwagger { }

Slide 121

Slide 121 text

buildscript { repositories { gradlePluginPortal() } dependencies { classpath "com.yelp.codegen:plugin:1.0.0" } } generateSwagger { inputFile = file("../sample_specs.json") }

Slide 122

Slide 122 text

buildscript { repositories { gradlePluginPortal() } dependencies { classpath "com.yelp.codegen:plugin:1.0.0" } } generateSwagger { inputFile = file("../sample_specs.json") outputDir = file("./src/main/java/") }

Slide 123

Slide 123 text

buildscript { repositories { gradlePluginPortal() } dependencies { classpath "com.yelp.codegen:plugin:1.0.0" } } generateSwagger { platform = "kotlin" packageName = "com.yelp.codegen.samples" specName = "petstore" specVersion = "1.0.0" inputFile = file("../sample_specs.json") outputDir = file("./src/main/java/") }

Slide 124

Slide 124 text

buildscript { repositories { gradlePluginPortal() } dependencies { classpath "com.yelp.codegen:plugin:1.0.0" } } generateSwagger { platform = "kotlin" packageName = "com.yelp.codegen.samples" specName = "petstore" specVersion = "1.0.0" inputFile = file("../sample_specs.json") outputDir = file("./src/main/java/") }

Slide 125

Slide 125 text

buildscript { repositories { gradlePluginPortal() } dependencies { classpath "com.yelp.codegen:plugin:1.0.0" } } generateSwagger { platform = "kotlin" packageName = "com.yelp.codegen.samples" specName = "petstore" specVersion = "1.0.0" inputFile = file("../sample_specs.json") outputDir = file("./src/main/java/") }

Slide 126

Slide 126 text

buildscript { repositories { gradlePluginPortal() } dependencies { classpath "com.yelp.codegen:plugin:1.0.0" } } generateSwagger { platform = "kotlin" packageName = "com.yelp.codegen.samples" specName = "petstore" specVersion = "1.0.0" inputFile = file("../sample_specs.json") outputDir = file("./src/main/java/") } preBuild.dependsOn(tasks.getByName(“generateSwagger"))

Slide 127

Slide 127 text

No content

Slide 128

Slide 128 text

No content

Slide 129

Slide 129 text

No content

Slide 130

Slide 130 text

Code Generation @ Yelp

Slide 131

Slide 131 text

No content

Slide 132

Slide 132 text

No content

Slide 133

Slide 133 text

No content

Slide 134

Slide 134 text

Mobile API Service ~400 endpoints BizApp Service ~100 endpoints

Slide 135

Slide 135 text

implementation "com.yelp.android.apis:mobileapi:13.20190320212515.0" implementation "com.yelp.android.apis:bizapp:13.20190320212515.0"

Slide 136

Slide 136 text

implementation "com.yelp.android.apis:mobileapi:13.20190320212515.0" implementation "com.yelp.android.apis:bizapp:13.20190320212515.0"

Slide 137

Slide 137 text

e pet of pet to return (required) ion-ID: getPetById") ") trofit2.http.Path("petId") petId: Long): Single eup.moshi.Json "name") var name: String, "photoUrls") var photoUrls: List, "category") var category: Category? = null, "id") var id: Long? = null, "status") var status: Pet.StatusEnum? = null tatusEnum(val value: String){ me = "available") AVAILABLE("available"), me = "sold") SOLD("sold")

Slide 138

Slide 138 text

Challenges & Future

Slide 139

Slide 139 text

Breaking changes Defining names Accessing the Raw Response SWAGGER GRADLE CODEGEN Yelp/swagger-gradle-codegen Challenges interface DefaultApi { /** * Find the owner of a pet. !*/ @GET("/pet/owner") fun getPetById( @retrofit2.http.Path("name") name: String @retrofit2.http.Path("surname") surname: String ): Single } interface DefaultApi { /** * Find the owner of a pet. !*/ @GET("/pet/owner") fun getPetById( @retrofit2.http.Path("surname") surname: String @retrofit2.http.Path("name") name: String ): Single } data class IdToPredictedBizInfoForPhotoUploadSuggestionMapToBusinessReviewMap( !!... ) interface DefaultApi { /** * Find the owner of a pet. !*/ @GET("/pet/owner") fun getPetById( @retrofit2.http.Path("surname") surname: String @retrofit2.http.Path("name") name: String ): Single } interface DefaultApi { /** * Find the owner of a pet. !*/ @GET("/pet/owner") fun getPetById( @retrofit2.http.Path("surname") surname: String @retrofit2.http.Path("name") name: String ): Single> }

Slide 140

Slide 140 text

Support Inheritance Coroutines iOS Template Getting a Corgi SWAGGER GRADLE CODEGEN Yelp/swagger-gradle-codegen Future

Slide 141

Slide 141 text

POST-/thank/you

Slide 142

Slide 142 text

We are hiring! www.yelp.com/careers

Slide 143

Slide 143 text

Questions?