|
| 1 | +// A structure to represent the information about a movie. |
| 2 | +// |
| 3 | +// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. |
| 4 | +// SPDX-License-Identifier: Apache-2.0 |
| 5 | + |
| 6 | +// snippet-start:[ddb.swift.batchgetitem.movie] |
| 7 | +import Foundation |
| 8 | +import AWSDynamoDB |
| 9 | + |
| 10 | +// snippet-start:[ddb.swift.batchgetitem.info] |
| 11 | +/// The optional details about a movie. |
| 12 | +public struct Info: Codable { |
| 13 | + /// The movie's rating, if available. |
| 14 | + var rating: Double? |
| 15 | + /// The movie's plot, if available. |
| 16 | + var plot: String? |
| 17 | +} |
| 18 | +// snippet-end:[ddb.swift.batchgetitem.info] |
| 19 | + |
| 20 | +public struct Movie: Codable { |
| 21 | + /// The year in which the movie was released. |
| 22 | + var year: Int |
| 23 | + /// The movie's title. |
| 24 | + var title: String |
| 25 | + /// An `Info` object providing the optional movie rating and plot |
| 26 | + /// information. |
| 27 | + var info: Info |
| 28 | + |
| 29 | + // snippet-start:[ddb.swift.batchgetitem.movie.init] |
| 30 | + /// Create a `Movie` object representing a movie, given the movie's |
| 31 | + /// details. |
| 32 | + /// |
| 33 | + /// - Parameters: |
| 34 | + /// - title: The movie's title (`String`). |
| 35 | + /// - year: The year in which the movie was released (`Int`). |
| 36 | + /// - rating: The movie's rating (optional `Double`). |
| 37 | + /// - plot: The movie's plot (optional `String`). |
| 38 | + init(title: String, year: Int, rating: Double? = nil, plot: String? = nil) { |
| 39 | + self.title = title |
| 40 | + self.year = year |
| 41 | + |
| 42 | + self.info = Info(rating: rating, plot: plot) |
| 43 | + } |
| 44 | + // snippet-end:[ddb.swift.batchgetitem.movie.init] |
| 45 | + |
| 46 | + // snippet-start:[ddb.swift.batchgetitem.movie.init-info] |
| 47 | + /// Create a `Movie` object representing a movie, given the movie's |
| 48 | + /// details. |
| 49 | + /// |
| 50 | + /// - Parameters: |
| 51 | + /// - title: The movie's title (`String`). |
| 52 | + /// - year: The year in which the movie was released (`Int`). |
| 53 | + /// - info: The optional rating and plot information for the movie in an |
| 54 | + /// `Info` object. |
| 55 | + init(title: String, year: Int, info: Info?) { |
| 56 | + self.title = title |
| 57 | + self.year = year |
| 58 | + |
| 59 | + if info != nil { |
| 60 | + self.info = info! |
| 61 | + } else { |
| 62 | + self.info = Info(rating: nil, plot: nil) |
| 63 | + } |
| 64 | + } |
| 65 | + // snippet-end:[ddb.swift.batchgetitem.movie.init-info] |
| 66 | + |
| 67 | + // snippet-start:[ddb.swift.batchgetitem.movie.init-withitem] |
| 68 | + /// |
| 69 | + /// Return a new `MovieTable` object, given an array mapping string to Amazon |
| 70 | + /// DynamoDB attribute values. |
| 71 | + /// |
| 72 | + /// - Parameter item: The item information provided in the form used by |
| 73 | + /// DynamoDB. This is an array of strings mapped to |
| 74 | + /// `DynamoDBClientTypes.AttributeValue` values. |
| 75 | + init(withItem item: [Swift.String:DynamoDBClientTypes.AttributeValue]) throws { |
| 76 | + // Read the attributes. |
| 77 | + |
| 78 | + guard let titleAttr = item["title"], |
| 79 | + let yearAttr = item["year"] else { |
| 80 | + throw MovieError.ItemNotFound |
| 81 | + } |
| 82 | + let infoAttr = item["info"] ?? nil |
| 83 | + |
| 84 | + // Extract the values of the title and year attributes. |
| 85 | + |
| 86 | + if case .s(let titleVal) = titleAttr { |
| 87 | + self.title = titleVal |
| 88 | + } else { |
| 89 | + throw MovieError.InvalidAttributes |
| 90 | + } |
| 91 | + |
| 92 | + if case .n(let yearVal) = yearAttr { |
| 93 | + self.year = Int(yearVal)! |
| 94 | + } else { |
| 95 | + throw MovieError.InvalidAttributes |
| 96 | + } |
| 97 | + |
| 98 | + // Extract the rating and/or plot from the `info` attribute, if |
| 99 | + // they're present. |
| 100 | + |
| 101 | + var rating: Double? = nil |
| 102 | + var plot: String? = nil |
| 103 | + |
| 104 | + if case .m(let infoVal) = infoAttr { |
| 105 | + let ratingAttr = infoVal["rating"] ?? nil |
| 106 | + let plotAttr = infoVal["plot"] ?? nil |
| 107 | + |
| 108 | + if ratingAttr != nil, case .n(let ratingVal) = ratingAttr { |
| 109 | + rating = Double(ratingVal) ?? nil |
| 110 | + } |
| 111 | + if plotAttr != nil, case .s(let plotVal) = plotAttr { |
| 112 | + plot = plotVal |
| 113 | + } |
| 114 | + } |
| 115 | + |
| 116 | + self.info = Info(rating: rating, plot: plot) |
| 117 | + } |
| 118 | + // snippet-end:[ddb.swift.batchgetitem.movie.init-withitem] |
| 119 | + |
| 120 | + // snippet-start:[ddb.swift.batchgetitem.movie.getasitem] |
| 121 | + /// |
| 122 | + /// Return an array mapping attribute names to Amazon DynamoDB attribute |
| 123 | + /// values, representing the contents of the `Movie` record as a DynamoDB |
| 124 | + /// item. |
| 125 | + /// |
| 126 | + /// - Returns: The movie item as an array of type |
| 127 | + /// `[Swift.String:DynamoDBClientTypes.AttributeValue]`. |
| 128 | + /// |
| 129 | + func getAsItem() async throws -> [Swift.String:DynamoDBClientTypes.AttributeValue] { |
| 130 | + // Build the item record, starting with the year and title, which are |
| 131 | + // always present. |
| 132 | + |
| 133 | + var item: [Swift.String:DynamoDBClientTypes.AttributeValue] = [ |
| 134 | + "year": .n(String(self.year)), |
| 135 | + "title": .s(self.title) |
| 136 | + ] |
| 137 | + |
| 138 | + // Add the `info` field with the rating and/or plot if they're |
| 139 | + // available. |
| 140 | + |
| 141 | + var info: [Swift.String:DynamoDBClientTypes.AttributeValue] = [:] |
| 142 | + if self.info.rating != nil { |
| 143 | + info["rating"] = .n(String(self.info.rating!)) |
| 144 | + } |
| 145 | + if self.info.plot != nil { |
| 146 | + info["plot"] = .s(self.info.plot!) |
| 147 | + } |
| 148 | + item["info"] = .m(info) |
| 149 | + |
| 150 | + return item |
| 151 | + } |
| 152 | + // snippet-end:[ddb.swift.batchgetitem.movie.getasitem] |
| 153 | +} |
| 154 | +// snippet-end:[ddb.swift.batchgetitem.movie] |
0 commit comments