First tests conclusive
This commit is contained in:
14
Package.resolved
Normal file
14
Package.resolved
Normal file
@@ -0,0 +1,14 @@
|
|||||||
|
{
|
||||||
|
"pins" : [
|
||||||
|
{
|
||||||
|
"identity" : "anycodable",
|
||||||
|
"kind" : "remoteSourceControl",
|
||||||
|
"location" : "https://github.com/Flight-School/AnyCodable.git",
|
||||||
|
"state" : {
|
||||||
|
"revision" : "862808b2070cd908cb04f9aafe7de83d35f81b05",
|
||||||
|
"version" : "0.6.7"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"version" : 2
|
||||||
|
}
|
||||||
@@ -6,7 +6,7 @@ import PackageDescription
|
|||||||
let package = Package(
|
let package = Package(
|
||||||
name: "swift-openfoodfacts-sdk",
|
name: "swift-openfoodfacts-sdk",
|
||||||
platforms: [
|
platforms: [
|
||||||
.macOS(.v14)
|
.macOS(.v14),
|
||||||
],
|
],
|
||||||
products: [
|
products: [
|
||||||
// Products define the executables and libraries a package produces, making them visible to other packages.
|
// Products define the executables and libraries a package produces, making them visible to other packages.
|
||||||
@@ -14,7 +14,10 @@ let package = Package(
|
|||||||
name: "swift-openfoodfacts-sdk",
|
name: "swift-openfoodfacts-sdk",
|
||||||
targets: ["swift-openfoodfacts-sdk"]
|
targets: ["swift-openfoodfacts-sdk"]
|
||||||
),
|
),
|
||||||
.executable(name: "exe", targets: ["exe"])
|
.executable(name: "exe", targets: ["exe"]),
|
||||||
|
],
|
||||||
|
dependencies: [
|
||||||
|
.package(url: "https://github.com/Flight-School/AnyCodable.git", from: "0.6.0"),
|
||||||
],
|
],
|
||||||
targets: [
|
targets: [
|
||||||
// Targets are the basic building blocks of a package, defining a module or a test suite.
|
// Targets are the basic building blocks of a package, defining a module or a test suite.
|
||||||
@@ -24,6 +27,7 @@ let package = Package(
|
|||||||
.executableTarget(name: "exe", dependencies: ["swift-openfoodfacts-sdk"]),
|
.executableTarget(name: "exe", dependencies: ["swift-openfoodfacts-sdk"]),
|
||||||
.testTarget(
|
.testTarget(
|
||||||
name: "swift-openfoodfacts-sdkTests",
|
name: "swift-openfoodfacts-sdkTests",
|
||||||
dependencies: ["swift-openfoodfacts-sdk"]),
|
dependencies: ["swift-openfoodfacts-sdk", "AnyCodable"]
|
||||||
|
),
|
||||||
]
|
]
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
import Foundation
|
import Foundation
|
||||||
|
|
||||||
public class OpenFoodFactsClient {
|
public class OpenFoodFactsClient {
|
||||||
let version: Int = 2
|
let version: Int = 0
|
||||||
public var prod: Bool = false
|
public var prod: Bool = false
|
||||||
var baseURL: URL? {
|
var baseURL: URL? {
|
||||||
if prod {
|
if prod {
|
||||||
@@ -16,7 +16,7 @@ public class OpenFoodFactsClient {
|
|||||||
|
|
||||||
public init() {}
|
public init() {}
|
||||||
|
|
||||||
public func getProductByBarcode(_ barcode: String) async throws -> Result {
|
public func getProductByBarcode(_ barcode: String) async throws -> ProductResponse {
|
||||||
guard let endpoint = baseURL?.appendingPathComponent("product/\(barcode)") else { throw OFFError.invalidURL }
|
guard let endpoint = baseURL?.appendingPathComponent("product/\(barcode)") else { throw OFFError.invalidURL }
|
||||||
var request = URLRequest(url: endpoint)
|
var request = URLRequest(url: endpoint)
|
||||||
request.setValue("application/json", forHTTPHeaderField: "accept")
|
request.setValue("application/json", forHTTPHeaderField: "accept")
|
||||||
@@ -26,230 +26,768 @@ public class OpenFoodFactsClient {
|
|||||||
throw OFFError.invalidResponse
|
throw OFFError.invalidResponse
|
||||||
}
|
}
|
||||||
do {
|
do {
|
||||||
return try JSONDecoder().decode(Result.self, from: data)
|
return try JSONDecoder().decode(ProductResponse.self, from: data)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public struct Result: Codable {
|
public struct Ingredient: Codable {
|
||||||
var code: String
|
var fromPalmOil: String? = nil
|
||||||
var status: Int
|
var id: String? = nil
|
||||||
var status_verbose: String
|
var origin: String? = nil
|
||||||
var product: Product
|
var percent: Float? = nil
|
||||||
}
|
var rank: Int? = 0
|
||||||
|
var text: String? = nil
|
||||||
|
var vegan: String? = nil
|
||||||
|
var vegetarian: String? = nil
|
||||||
|
|
||||||
public struct Product: Codable {
|
private enum CodingKeys: String, CodingKey {
|
||||||
var abbreviated_product_name: String // Abbreviated name in requested language
|
case fromPalmOil = "from_palm_oil"
|
||||||
var code: String // barcode of the product (can be EAN-13 or internal codes for some food stores), for products without a barcode, Open Food Facts assigns a number starting with the 200 reserved prefix
|
case id
|
||||||
var codes_tags: [String] // A value which is the type of barcode "code-13" or "code-8" and A series of mask for the barcode It helps retrieve barcodes starting by ]
|
case origin
|
||||||
var generic_name: String // Legal name of the product as regulated by the European authorities.
|
case percent
|
||||||
var id: String // internal identifier for the product, usually set to the value of code, except on the producers platform where it is prefixed by the owner
|
case rank
|
||||||
var lc: String // Main language of the product. This is a duplicate of lang property (for historical reasons).
|
case text
|
||||||
var lang: String // Main language of the product.
|
case vegan
|
||||||
// This should be the main language of product packaging (if one is predominant).
|
case vegetarian
|
||||||
// Main language is also used to decide which ingredients list to parse.
|
|
||||||
var nova_group: Int // Nova group as an Int from 1 to 4. See https://world.openfoodfacts.org/nova
|
|
||||||
var nova_groups: String
|
|
||||||
var obsolete: String
|
|
||||||
var obsolete_since_date: String // A date at which the product was declared obsolete. This means it's not produced any more.
|
|
||||||
var product_name: String // The name of the product
|
|
||||||
var product_name_en: String // The name of the product can also be in many other languages like product_name_fr (for French).
|
|
||||||
var product_quantity: String // The size in g or ml for the whole product. It's a normalized version of the quantity field.
|
|
||||||
var quantity: String // Quantity and Unit.
|
|
||||||
var additives_n: Int // Number of food additives.
|
|
||||||
var checked: String
|
|
||||||
var complete: Int
|
|
||||||
var completeness: Float
|
|
||||||
var food_groups: String
|
|
||||||
var food_groups_tags: [String]
|
|
||||||
var nutrient_levels: NutrientLevel
|
|
||||||
|
|
||||||
var pnns_groups_1: String // Category of food according to French Nutrition and Health Program
|
|
||||||
var pnns_groups_1_tags: [String]
|
|
||||||
var pnns_groups_2: String // Sub Category of food according to French Nutrition and Health Program
|
|
||||||
var pnns_groups_2_tags: [String]
|
|
||||||
var popularity_key: Int
|
|
||||||
var popularity_tags: [String]
|
|
||||||
var scans_n: Int
|
|
||||||
var unique_scans_n: Int
|
|
||||||
var serving_quantity: String // Normalized version of serving_size.Note that this is NOT the number of servings by product.(in perl, see normalize_serving_size)
|
|
||||||
var serving_size: String // Serving size text(generally in g or ml).We expect a quantity + unit but the user is free to input any string.
|
|
||||||
var brands: String
|
|
||||||
var brands_tags: [String]
|
|
||||||
var categories: String
|
|
||||||
var categories_hierarchy: [String]
|
|
||||||
var categories_lc: String
|
|
||||||
var categories_tags: [String]
|
|
||||||
var checkers_tags: [String]
|
|
||||||
var countries: String // List of countries where the product is sold.
|
|
||||||
var countries_hierarchy: [String]
|
|
||||||
var countries_lc: String
|
|
||||||
var countries_tags: [String]
|
|
||||||
var manufacturing_places: String
|
|
||||||
var nutrient_levels_tags: [String]
|
|
||||||
var image_front_small_url: String
|
|
||||||
var image_front_thumb_url: String
|
|
||||||
var image_front_url: String
|
|
||||||
var image_nutrition_small_url: String
|
|
||||||
var image_nutrition_thumb_url: String
|
|
||||||
var image_nutrition_url: String
|
|
||||||
var image_small_url: String
|
|
||||||
var image_thumb_url: String
|
|
||||||
var image_url: String
|
|
||||||
var ingredients: [Ingredient]
|
|
||||||
var nutriments: Nutrition.Nutriments
|
|
||||||
|
|
||||||
public struct NutrientLevel: Codable {
|
|
||||||
var fat: TrafficLightIndicator
|
|
||||||
var salt: TrafficLightIndicator
|
|
||||||
var saturated_fat: TrafficLightIndicator
|
|
||||||
var sugars: TrafficLightIndicator
|
|
||||||
|
|
||||||
public enum TrafficLightIndicator: String, Codable {
|
|
||||||
case low
|
|
||||||
case moderate
|
|
||||||
case high
|
|
||||||
}
|
|
||||||
|
|
||||||
enum CodingKeys: String, CodingKey {
|
|
||||||
case fat, salt, sugars
|
|
||||||
case saturated_fat = "saturated-fat"
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public class Ingredient: Codable {
|
public struct LanguagesCodes: Codable {
|
||||||
var additives_tags: [String]?
|
var en: String? = nil
|
||||||
var allergens: String?
|
var fr: String? = nil
|
||||||
var allergens_lc: String?
|
var pl: String? = nil
|
||||||
var allergens_hierarchy: [String]?
|
|
||||||
var allergens_tags: [String]?
|
|
||||||
var id: String
|
|
||||||
var percent_estimate: Float?
|
|
||||||
var percent_max: Float?
|
|
||||||
var percent_min: Float?
|
|
||||||
var text: String?
|
|
||||||
var vegan: String?
|
|
||||||
var vegetarian: String?
|
|
||||||
var ingredients: [Ingredient]?
|
|
||||||
var ingredients_analysis: IngredientAnalysis?
|
|
||||||
var ingredients_analysis_tags: [String]?
|
|
||||||
var ingredients_from_or_that_may_be_from_palm_oil_n: Int?
|
|
||||||
var ingredients_from_palm_oil_n: Int?
|
|
||||||
var ingredients_hierarchy: [String]?
|
|
||||||
var ingredients_n: Int?
|
|
||||||
var ingredients_n_tags: [String]?
|
|
||||||
var ingredients_original_tags: [String]?
|
|
||||||
var ingredients_percent_analysis: Int?
|
|
||||||
var ingredients_tags: [String]?
|
|
||||||
var ingredients_lc: String? // Language that was used to parse the ingredient list. If ingredients_text is available for the product main language (lang), ingredients_lc=lang, otherwise we look at ingredients_text fields for other languages and set ingredients_lc to the first non-empty ingredient_text.
|
|
||||||
var ingredients_text: String? // Raw list of ingredients. This will get automatically parsed and get used to compute the Eco-Score or find allergens, etc..
|
|
||||||
// It's a copy of ingredients_text in the main language of the product (see lang proprety).
|
|
||||||
var ingredients_text_with_allergens: String? // Same text as ingredients_text but where allergens have HTML elements around them to identify them
|
|
||||||
var ingredients_that_may_be_from_palm_oil_n: Int?
|
|
||||||
var ingredients_with_specified_percent_n: Int?
|
|
||||||
var ingredients_with_specified_percent_sum: Int?
|
|
||||||
var ingredients_with_unspecified_percent_n: Int?
|
|
||||||
var ingredients_with_unspecified_percent_sum: Int?
|
|
||||||
var known_ingredients_n: Int?
|
|
||||||
var origins: String?
|
|
||||||
var origins_lc: String?
|
|
||||||
var traces: String?
|
|
||||||
var unknown_ingredients_n: Int?
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public struct IngredientAnalysis: Codable {
|
public struct NutrientLevels: Codable {
|
||||||
var palmOil: [String]?
|
private var fat: String? = nil
|
||||||
var vegan: [String]?
|
private var salt: String? = nil
|
||||||
var vegetarian: [String]?
|
private var saturatedFat: String? = nil
|
||||||
|
private var sugars: String? = nil
|
||||||
|
|
||||||
enum CodingKeys: String, CodingKey {
|
private enum CodingKeys: String, CodingKey {
|
||||||
case palmOil = "en:palm-oil"
|
case fat
|
||||||
case vegan = "en:vegan-status-unknown"
|
case salt
|
||||||
case vegetarian = "en:vegetarian-status-unknown"
|
case saturatedFat = "saturated-fat"
|
||||||
|
case sugars
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public struct Nutrition: Codable {
|
|
||||||
var no_nutrition_data: String? // When a product does not have nutrition data displayed on the packaging, the user can check the field "Nutrition facts are not specified on the product". By doing so, the no_nutrition_data field takes the value "on". This case is frequent (thousands of products).
|
|
||||||
var nutrition_data_per: ServingKind // ➔ The nutrition data on the package can be per serving or per 100g.
|
|
||||||
// This is essential to understand if <nutrient>_value and <nutrient> values in nutriments applies for a serving or for 100g.
|
|
||||||
// IMPORTANT: When writing products, this setting applies to all existing nutrients values for the product, not only the nutrient values sent in the write request. So it should not be changed unless all nutrients values are provided with values that match the nutrition_data_per field.
|
|
||||||
// Allowed: serving┃100g
|
|
||||||
var nutrition_data_prepared_per: ServingKind
|
|
||||||
|
|
||||||
public enum ServingKind: String, Codable {
|
|
||||||
case serving
|
|
||||||
case hundredGrams = "100g"
|
|
||||||
}
|
|
||||||
|
|
||||||
var nutriments: Nutriments
|
|
||||||
|
|
||||||
public struct Nutriments: Codable {
|
public struct Nutriments: Codable {
|
||||||
var alcohol: Float // Quantity of alcohol (per 100g or per serving) in a standard unit (g or ml)
|
var calcium: Float? = 0.0
|
||||||
var carbohydrates: Float
|
var calciumValue: Float? = 0.0
|
||||||
var energy: Float // It is the same as energy-kj if we have it, or computed from energy-kcal otherwise (per 100g or per serving) in kj
|
var calcium100G: Float? = 0.0
|
||||||
var energy_value: Float // energy_value will be equal to energy-kj_value if we have it or to energy-kcal_value otherwise
|
var calciumServing: Float? = 0.0
|
||||||
var energy_unit: EnergyUnit // Equal to energy-kj_unit if we have it or to energy-kcal_unit otherwise Allowed: kcal┃kj
|
var calciumUnit: String? = nil
|
||||||
var energyKcal: Float // energy-kcal, energy in kcal, if it is specified (per 100g or per serving) in a standard unit (g or ml)
|
|
||||||
var energyKj: Float // energy in kj, if it is specified (per 100g or per serving) in a standard unit (g or ml)
|
|
||||||
var fat: Float
|
|
||||||
var fruitsVegetablesLegumesEstimateFromIngredients: Float // An estimate, from the ingredients list of the percentage of fruits, vegetable and legumes. This is an important information for Nutri-Score (2023 version) computation.
|
|
||||||
var fruitsVegetablesNutsEstimateFromIngredients: Float
|
|
||||||
var proteins: Float
|
|
||||||
var salt: Float
|
|
||||||
var saturatedFat: Float
|
|
||||||
var sodium: Float
|
|
||||||
var sugars: Float
|
|
||||||
var erythritol: Float?
|
|
||||||
|
|
||||||
// pattern: (?<nutrient>[\w-]+)_unit]: enum
|
var carbohydrates: Float? = 0.0
|
||||||
// The unit in which the nutrient for 100g or per serving is measured.
|
var carbohydratesValue: Float? = 0.0
|
||||||
// The possible values depends on the nutrient.
|
var carbohydrates100G: Float? = 0.0
|
||||||
// g for grams
|
var carbohydratesServing: Float? = 0.0
|
||||||
// mg for milligrams
|
var carbohydratesUnit: String? = nil
|
||||||
// μg for micrograms
|
|
||||||
// cl for centiliters
|
|
||||||
// ml for mililiters
|
|
||||||
// dv for recommended daily intakes (aka Dietary Reference Intake)
|
|
||||||
// % vol for alcohol vol per 100 ml
|
|
||||||
// 🤓 code: see the Units module, and Food:default_unit_for_nid function
|
|
||||||
// Allowed: 公斤┃公升┃kg┃кг┃l┃л┃毫克┃mg┃мг┃mcg┃µg┃oz┃fl oz┃dl┃дл┃cl┃кл┃斤┃g┃∅┃●┃kj┃克┃公克┃г┃мл┃ml┃mmol/l┃毫升┃% vol┃ph┃%┃% dv┃% vol (alcohol)┃iu┃mol/l┃mval/l┃ppm┃<EFBFBD>rh┃<EFBFBD>fh┃<EFBFBD>e┃<EFBFBD>dh┃gpg
|
|
||||||
// [pattern: (?<nutrient>[\w-]+)_100g]: number
|
|
||||||
// The standardized value of a serving of 100g (or 100ml for liquids) for the nutrient.
|
|
||||||
// This is computed from the nutrient property, the serving size (if needed), and the nutrient_unit field.
|
|
||||||
// Note: If you want to characterize products in a uniform way, this is the value you should use.
|
|
||||||
// [pattern: (?<nutrient>[\w-]+)_serving]: number
|
|
||||||
// The standardized value of a serving for this product.
|
|
||||||
// [pattern: (?<nutrient>[\w-]+)_value]: number
|
|
||||||
// The value input by the user / displayed on the product for the nutrient.
|
|
||||||
// per 100g or serving, depending on nutrition_data_per
|
|
||||||
// in the unit of corresponding _unit field.
|
|
||||||
// [pattern: (?<nutrient>[\w-]+)_prepared]: number
|
|
||||||
// The value for nutrient for prepared product.
|
|
||||||
// [pattern: (?<nutrient>[\w-]+)_prepared_unit]: string
|
|
||||||
// The unit in which the nutrient of prepared product is measured.
|
|
||||||
// [pattern: (?<nutrient>[\w-]+)_prepared_100g]: number
|
|
||||||
// The standardized value of a serving of 100g (or 100ml for liquids) for the nutrient, for prepared product.
|
|
||||||
// [pattern: (?<nutrient>[\w-]+)_prepared_serving]: number
|
|
||||||
// The standardized value of a serving for the prepared product.
|
|
||||||
// [pattern: (?<nutrient>[\w-]+)_prepared_value]: number
|
|
||||||
|
|
||||||
public enum EnergyUnit: String, Codable {
|
var carbonFootprintFromKnownIngredientsProduct: Float? = 0.0
|
||||||
case kcal, kJ
|
var carbonFootprintFromKnownIngredients100G: Float? = 0.0
|
||||||
}
|
var carbonFootprintFromKnownIngredientsServing: Float? = 0.0
|
||||||
|
|
||||||
enum CodingKeys: String, CodingKey {
|
var cholesterol: Float? = 0.0
|
||||||
case alcohol, carbohydrates, energy, energy_value, energy_unit, fat, proteins, salt, sodium, sugars, erythritol
|
var cholesterolValue: Float? = 0.0
|
||||||
|
var cholesterol100G: Float? = 0.0
|
||||||
|
var cholesterolServing: Float? = 0.0
|
||||||
|
var cholesterolUnit: String? = nil
|
||||||
|
|
||||||
|
var energy: Int? = 0
|
||||||
|
var energyKcal: Int? = 0
|
||||||
|
var energyKj: Int? = 0
|
||||||
|
var energyValue: Int? = 0
|
||||||
|
var energyKcalValue: Int? = 0
|
||||||
|
var energyKjValue: Int? = 0
|
||||||
|
var energy100G: Int? = 0
|
||||||
|
var energyKcal100G: Int? = 0
|
||||||
|
var energyKj100G: Int? = 0
|
||||||
|
var energyServing: Int? = 0
|
||||||
|
var energyKcalServing: Double? = 0.0
|
||||||
|
var energyKjServing: Int? = 0
|
||||||
|
var energyUnit: String? = nil
|
||||||
|
var energyKcalUnit: String? = nil
|
||||||
|
var energyKjUnit: String? = nil
|
||||||
|
|
||||||
|
var fat: Float? = 0.0
|
||||||
|
var fatValue: Float? = 0.0
|
||||||
|
var fat100G: Float? = 0.0
|
||||||
|
var fatServing: Float? = 0.0
|
||||||
|
var fatUnit: String? = nil
|
||||||
|
|
||||||
|
var fiber: Float? = 0.0
|
||||||
|
var fiberValue: Float? = 0.0
|
||||||
|
var fiber100G: Float? = 0.0
|
||||||
|
var fiberServing: Float? = 0.0
|
||||||
|
var fiberUnit: String? = nil
|
||||||
|
|
||||||
|
var fruitsVegetablesNutsEstimateFromIngredients100G: Float? = 0.0
|
||||||
|
|
||||||
|
var iron: Float? = 0.0
|
||||||
|
var ironValue: Float? = 0.0
|
||||||
|
var iron100G: Float? = 0.0
|
||||||
|
var ironServing: Float? = 0.0
|
||||||
|
var ironUnit: String? = nil
|
||||||
|
|
||||||
|
var novaGroup: Float? = 0.0
|
||||||
|
var novaGroup100G: Float? = 0.0
|
||||||
|
var novaGroupServing: Float? = 0.0
|
||||||
|
|
||||||
|
var proteins: Float? = 0.0
|
||||||
|
var proteinsValue: Float? = 0.0
|
||||||
|
var proteins100G: Float? = 0.0
|
||||||
|
var proteinsServing: Float? = 0.0
|
||||||
|
var proteinsUnit: String? = nil
|
||||||
|
|
||||||
|
var salt: Float? = 0.0
|
||||||
|
var saltValue: Float? = 0.0
|
||||||
|
var salt100G: Float? = 0.0
|
||||||
|
var saltServing: Float? = 0.0
|
||||||
|
var saltUnit: String? = nil
|
||||||
|
|
||||||
|
var saturatedFat: Float? = 0.0
|
||||||
|
var saturatedFatValue: Float? = 0.0
|
||||||
|
var saturatedFat100G: Float? = 0.0
|
||||||
|
var saturatedFatServing: Float? = 0.0
|
||||||
|
var saturatedFatUnit: String? = nil
|
||||||
|
|
||||||
|
var sodium: Float? = 0.0
|
||||||
|
var sodiumValue: Float? = 0.0
|
||||||
|
var sodium100G: Float? = 0.0
|
||||||
|
var sodiumServing: Float? = 0.0
|
||||||
|
var sodiumUnit: String? = nil
|
||||||
|
|
||||||
|
var sugars: Float? = 0.0
|
||||||
|
var sugarsValue: Float? = 0.0
|
||||||
|
var sugars100G: Float? = 0.0
|
||||||
|
var sugarsServing: Float? = 0.0
|
||||||
|
var sugarsUnit: String? = nil
|
||||||
|
|
||||||
|
var transFat: Float? = 0.0
|
||||||
|
var transFatValue: Float? = 0.0
|
||||||
|
var transFat100G: Float? = 0.0
|
||||||
|
var transFatServing: Float? = 0.0
|
||||||
|
var transFatUnit: String? = nil
|
||||||
|
|
||||||
|
var vitaminA: Float? = 0.0
|
||||||
|
var vitaminAValue: Float? = 0.0
|
||||||
|
var vitaminA100G: Float? = 0.0
|
||||||
|
var vitaminAServing: Float? = 0.0
|
||||||
|
var vitaminAUnit: String? = nil
|
||||||
|
|
||||||
|
var vitaminC: Float? = 0.0
|
||||||
|
var vitaminCValue: Float? = 0.0
|
||||||
|
var vitaminC100G: Float? = 0.0
|
||||||
|
var vitaminCServing: Float? = 0.0
|
||||||
|
var vitaminCUnit: String? = nil
|
||||||
|
|
||||||
|
var vitaminD: Float? = 0.0
|
||||||
|
var vitaminDValue: Float? = 0.0
|
||||||
|
var vitaminD100G: Float? = 0.0
|
||||||
|
var vitaminDServing: Float? = 0.0
|
||||||
|
var vitaminDUnit: String? = nil
|
||||||
|
|
||||||
|
// var other: [String: Any] = [:]
|
||||||
|
//
|
||||||
|
// mutating func setDetail(key: String, value: Any) {
|
||||||
|
// other[key] = value
|
||||||
|
// }
|
||||||
|
|
||||||
|
private enum CodingKeys: String, CodingKey {
|
||||||
|
case calcium
|
||||||
|
case calciumValue = "calcium_value"
|
||||||
|
case calcium100G = "calcium_100g"
|
||||||
|
case calciumServing = "calcium_serving"
|
||||||
|
case calciumUnit = "calcium_unit"
|
||||||
|
|
||||||
|
case carbohydrates
|
||||||
|
case carbohydratesValue = "carbohydrates_value"
|
||||||
|
case carbohydrates100G = "carbohydrates_100g"
|
||||||
|
case carbohydratesServing = "carbohydrates_serving"
|
||||||
|
case carbohydratesUnit = "carbohydrates_unit"
|
||||||
|
|
||||||
|
case carbonFootprintFromKnownIngredientsProduct = "carbon-footprint-from-known-ingredients_product"
|
||||||
|
case carbonFootprintFromKnownIngredients100G = "carbon-footprint-from-known-ingredients_100g"
|
||||||
|
case carbonFootprintFromKnownIngredientsServing = "carbon-footprint-from-known-ingredients_serving"
|
||||||
|
|
||||||
|
case cholesterol
|
||||||
|
case cholesterolValue = "cholesterol_value"
|
||||||
|
case cholesterol100G = "cholesterol_100g"
|
||||||
|
case cholesterolServing = "cholesterol_serving"
|
||||||
|
case cholesterolUnit = "cholesterol_unit"
|
||||||
|
|
||||||
|
case energy
|
||||||
case energyKcal = "energy-kcal"
|
case energyKcal = "energy-kcal"
|
||||||
case energyKj = "energy-kj"
|
case energyKj = "energy-kj"
|
||||||
case fruitsVegetablesLegumesEstimateFromIngredients = "fruits-vegetables-legumes-estimate-from-ingredients"
|
case energyValue = "energy_value"
|
||||||
case fruitsVegetablesNutsEstimateFromIngredients = "fruits-vegetables-nuts-estimate-from-ingredients"
|
case energyKcalValue = "energy-kcal_value"
|
||||||
|
case energyKjValue = "energy-kj_value"
|
||||||
|
case energy100G = "energy_100g"
|
||||||
|
case energyKcal100G = "energy-kcal_100g"
|
||||||
|
case energyKj100G = "energy-kj_100g"
|
||||||
|
case energyServing = "energy_serving"
|
||||||
|
case energyKcalServing = "energy-kcal_serving"
|
||||||
|
case energyKjServing = "energy-kj_serving"
|
||||||
|
case energyUnit = "energy_unit"
|
||||||
|
case energyKcalUnit = "energy-kcal_unit"
|
||||||
|
case energyKjUnit = "energy-kj_unit"
|
||||||
|
|
||||||
|
case fat
|
||||||
|
case fatValue = "fat_value"
|
||||||
|
case fat100G = "fat_100g"
|
||||||
|
case fatServing = "fat_serving"
|
||||||
|
case fatUnit = "fat_unit"
|
||||||
|
|
||||||
|
case fiber
|
||||||
|
case fiberValue = "fiber_value"
|
||||||
|
case fiber100G = "fiber_100g"
|
||||||
|
case fiberServing = "fiber_serving"
|
||||||
|
case fiberUnit = "fiber_unit"
|
||||||
|
|
||||||
|
case fruitsVegetablesNutsEstimateFromIngredients100G = "fruits-vegetables-nuts-estimate-from-ingredients_100g"
|
||||||
|
|
||||||
|
case iron
|
||||||
|
case ironValue = "iron_value"
|
||||||
|
case iron100G = "iron_100g"
|
||||||
|
case ironServing = "iron_serving"
|
||||||
|
case ironUnit = "iron_unit"
|
||||||
|
|
||||||
|
case novaGroup
|
||||||
|
case novaGroup100G = "nova-group_100g"
|
||||||
|
case novaGroupServing = "nova-group_serving"
|
||||||
|
|
||||||
|
case proteins
|
||||||
|
case proteinsValue = "proteins_value"
|
||||||
|
case proteins100G = "proteins_100g"
|
||||||
|
case proteinsServing = "proteins_serving"
|
||||||
|
case proteinsUnit = "proteins_unit"
|
||||||
|
|
||||||
|
case salt
|
||||||
|
case saltValue = "salt_value"
|
||||||
|
case salt100G = "salt_100g"
|
||||||
|
case saltServing = "salt_serving"
|
||||||
|
case saltUnit = "salt_unit"
|
||||||
|
|
||||||
case saturatedFat = "saturated-fat"
|
case saturatedFat = "saturated-fat"
|
||||||
}
|
case saturatedFatValue = "saturated-fat_value"
|
||||||
}
|
case saturatedFat100G = "saturated-fat_100g"
|
||||||
|
case saturatedFatServing = "saturated-fat_serving"
|
||||||
|
case saturatedFatUnit = "saturated-fat_unit"
|
||||||
|
|
||||||
|
case sodium
|
||||||
|
case sodiumValue = "sodium_value"
|
||||||
|
case sodium100G = "sodium_100g"
|
||||||
|
case sodiumServing = "sodium_serving"
|
||||||
|
case sodiumUnit = "sodium_unit"
|
||||||
|
|
||||||
|
case sugars
|
||||||
|
case sugarsValue = "sugars_value"
|
||||||
|
case sugars100G = "sugars_100g"
|
||||||
|
case sugarsServing = "sugars_serving"
|
||||||
|
case sugarsUnit = "sugars_unit"
|
||||||
|
|
||||||
|
case transFat = "trans-fat"
|
||||||
|
case transFatValue = "trans-fat_value"
|
||||||
|
case transFat100G = "trans-fat_100g"
|
||||||
|
case transFatServing = "trans-fat_serving"
|
||||||
|
case transFatUnit = "trans-fat_unit"
|
||||||
|
|
||||||
|
case vitaminA = "vitamin-a"
|
||||||
|
case vitaminAValue = "vitamin-a_value"
|
||||||
|
case vitaminA100G = "vitamin-a_100g"
|
||||||
|
case vitaminAServing = "vitamin-a_serving"
|
||||||
|
case vitaminAUnit = "vitamin-a_unit"
|
||||||
|
|
||||||
|
case vitaminC = "vitamin-c"
|
||||||
|
case vitaminCValue = "vitamin-c_value"
|
||||||
|
case vitaminC100G = "vitamin-c_100g"
|
||||||
|
case vitaminCServing = "vitamin-c_serving"
|
||||||
|
case vitaminCUnit = "vitamin-c_unit"
|
||||||
|
|
||||||
|
case vitaminD = "vitamin-d"
|
||||||
|
case vitaminDValue = "vitamin-d_value"
|
||||||
|
case vitaminD100G = "vitamin-d_100g"
|
||||||
|
case vitaminDServing = "vitamin-d_serving"
|
||||||
|
case vitaminDUnit = "vitamin-d_unit"
|
||||||
|
|
||||||
|
// case other
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
enum OFFError: Error {
|
public struct ProductResponse: Codable {
|
||||||
case invalidURL, invalidResponse
|
var product: Product?
|
||||||
|
var code: String?
|
||||||
|
var status: Int? // or Bool, depending on your needs
|
||||||
|
var statusVerbose: String?
|
||||||
|
|
||||||
|
private enum CodingKeys: String, CodingKey {
|
||||||
|
case product
|
||||||
|
case code
|
||||||
|
case status
|
||||||
|
case statusVerbose = "status_verbose"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public struct SelectedImages: Codable {
|
||||||
|
let front: SelectedImage?
|
||||||
|
let ingredients: SelectedImage?
|
||||||
|
let nutrition: SelectedImage?
|
||||||
|
}
|
||||||
|
|
||||||
|
public class SelectedImage: Codable {
|
||||||
|
var display: SelectedImageItem?
|
||||||
|
var small: SelectedImageItem?
|
||||||
|
var thumb: SelectedImageItem?
|
||||||
|
}
|
||||||
|
|
||||||
|
public struct SelectedImageItem: Codable {
|
||||||
|
let en: String?
|
||||||
|
let fr: String?
|
||||||
|
let pl: String?
|
||||||
|
|
||||||
|
var url: String {
|
||||||
|
[en, fr, pl].compactMap { $0 }.first ?? ""
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// public struct Images: Codable {
|
||||||
|
// private var otherData: [String: Data] = [:]
|
||||||
|
|
||||||
|
// mutating func setDetail<T: Encodable>(key: String, value: T) throws {
|
||||||
|
// let encodedValue = try JSONEncoder().encode(value)
|
||||||
|
// otherData[key] = encodedValue
|
||||||
|
// }
|
||||||
|
|
||||||
|
// func getDetail<T: Decodable>(key: String, type: T.Type) throws -> T? {
|
||||||
|
// guard let data = otherData[key] else { return nil }
|
||||||
|
// return try JSONDecoder().decode(type, from: data)
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
public struct Source: Codable {
|
||||||
|
let fields: [String] = []
|
||||||
|
let id: String? = nil
|
||||||
|
let images: [String] = []
|
||||||
|
let importT: Int = 0
|
||||||
|
let manufacturer: String? = nil
|
||||||
|
let name: String? = nil
|
||||||
|
let url: String? = nil
|
||||||
|
|
||||||
|
private enum CodingKeys: String, CodingKey {
|
||||||
|
case fields
|
||||||
|
case id
|
||||||
|
case images
|
||||||
|
case importT = "import_t"
|
||||||
|
case manufacturer
|
||||||
|
case name
|
||||||
|
case url
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public class Product: Codable {
|
||||||
|
// var images: Images? = Images()
|
||||||
|
var ingredients: [Ingredient]? = []
|
||||||
|
var languagesCodes: LanguagesCodes?
|
||||||
|
var nutrientLevels: NutrientLevels?
|
||||||
|
var nutriments: Nutriments? = Nutriments()
|
||||||
|
var selectedImages: SelectedImages?
|
||||||
|
var sources: [Source]? = []
|
||||||
|
var additivesN: Int?
|
||||||
|
var additivesOldN: Int?
|
||||||
|
var additivesOriginalTags: [String]?
|
||||||
|
var additivesOldTags: [String]?
|
||||||
|
var additivesPrevOriginalTags: [String]?
|
||||||
|
var additivesDebugTags: [String]?
|
||||||
|
var additivesTags: [String]?
|
||||||
|
var allergens: String?
|
||||||
|
var allergensFromIngredients: String?
|
||||||
|
var allergensFromUser: String?
|
||||||
|
var allergensHierarchy: [String]?
|
||||||
|
var allergensLc: String?
|
||||||
|
var allergensTags: [String]?
|
||||||
|
var aminoAcidsPrevTags: [String]?
|
||||||
|
var aminoAcidsTags: [String]?
|
||||||
|
var brands: String?
|
||||||
|
var brandsDebugTags: [String]?
|
||||||
|
var brandsTags: [String]?
|
||||||
|
var carbonFootprintPercentOfKnownIngredients: String?
|
||||||
|
var carbonFootprintFromKnownIngredientsDebug: String?
|
||||||
|
var categories: String?
|
||||||
|
var categoriesHierarchy: [String]?
|
||||||
|
var categoriesLc: String?
|
||||||
|
var categoriesPropertiesTags: [String]?
|
||||||
|
var categoriesTags: [String]?
|
||||||
|
var checkersTags: [String]?
|
||||||
|
var citiesTags: [String]?
|
||||||
|
var code: String?
|
||||||
|
var codesTags: [String]?
|
||||||
|
var comparedToCategory: String?
|
||||||
|
var complete: Int?
|
||||||
|
var completedT: Int?
|
||||||
|
var completeness: Double?
|
||||||
|
var conservationConditions: String?
|
||||||
|
var countries: String?
|
||||||
|
var countriesHierarchy: [String]?
|
||||||
|
var countriesLc: String?
|
||||||
|
var countriesDebugTags: [String]?
|
||||||
|
var countriesTags: [String]?
|
||||||
|
var correctorsTags: [String]?
|
||||||
|
var createdT: Int?
|
||||||
|
var creator: String?
|
||||||
|
var dataQualityBugsTags: [String]?
|
||||||
|
var dataQualityErrorsTags: [String]?
|
||||||
|
var dataQualityInfoTags: [String]?
|
||||||
|
var dataQualityTags: [String]?
|
||||||
|
var dataQualityWarningsTags: [String]?
|
||||||
|
var dataSources: String?
|
||||||
|
var dataSourcesTags: [String]?
|
||||||
|
var debugParamSortedLangs: [String]?
|
||||||
|
var editorsTags: [String]?
|
||||||
|
var embCodes: String?
|
||||||
|
var embCodesDebugTags: [String]?
|
||||||
|
var embCodesOrig: String?
|
||||||
|
var embCodesTags: [String]?
|
||||||
|
var entryDatesTags: [String]?
|
||||||
|
var expirationDate: String?
|
||||||
|
var expirationDateDebugTags: [String]?
|
||||||
|
var fruitsVegetablesNuts100GEstimate: Int?
|
||||||
|
var genericName: String?
|
||||||
|
var id: String?
|
||||||
|
var _id: String?
|
||||||
|
var imageFrontSmallUrl: String?
|
||||||
|
var imageFrontThumbUrl: String?
|
||||||
|
var imageFrontUrl: String?
|
||||||
|
var imageIngredientsUrl: String?
|
||||||
|
var imageIngredientsSmallUrl: String?
|
||||||
|
var imageIngredientsThumbUrl: String?
|
||||||
|
var imageNutritionSmallUrl: String?
|
||||||
|
var imageNutritionThumbUrl: String?
|
||||||
|
var imageNutritionUrl: String?
|
||||||
|
var imageSmallUrl: String?
|
||||||
|
var imageThumbUrl: String?
|
||||||
|
var imageUrl: String?
|
||||||
|
var informersTags: [String]?
|
||||||
|
var ingredientsAnalysisTags: [String]?
|
||||||
|
var ingredientsDebug: [String?]?
|
||||||
|
var ingredientsFromOrThatMayBeFromPalmOilN: Int?
|
||||||
|
var ingredientsFromPalmOilTags: [String]?
|
||||||
|
var ingredientsFromPalmOilN: Int?
|
||||||
|
var ingredientsHierarchy: [String]?
|
||||||
|
var ingredientsIdsDebug: [String]?
|
||||||
|
var ingredientsN: Int?
|
||||||
|
var ingredientsNTags: [String]?
|
||||||
|
var ingredientsOriginalTags: [String]?
|
||||||
|
var ingredientsTags: [String]?
|
||||||
|
var ingredientsText: String?
|
||||||
|
var ingredientsTextDebug: String?
|
||||||
|
var ingredientsTextWithAllergens: String?
|
||||||
|
var ingredientsThatMayBeFromPalmOilN: Int?
|
||||||
|
var ingredientsThatMayBeFromPalmOilTags: [String]?
|
||||||
|
var interfaceVersionCreated: String?
|
||||||
|
var interfaceVersionModified: String?
|
||||||
|
var keywords: [String]?
|
||||||
|
var knownIngredientsN: Int?
|
||||||
|
var labels: String?
|
||||||
|
var labelsHierarchy: [String]?
|
||||||
|
var labelsLc: String?
|
||||||
|
var labelsPrevHierarchy: [String]?
|
||||||
|
var labelsPrevTags: [String]?
|
||||||
|
var labelsTags: [String]?
|
||||||
|
var labelsDebugTags: [String]?
|
||||||
|
var lang: String?
|
||||||
|
var langDebugTags: [String]?
|
||||||
|
var languagesHierarchy: [String]?
|
||||||
|
var languagesTags: [String]?
|
||||||
|
var lastEditDatesTags: [String]?
|
||||||
|
var lastEditor: String?
|
||||||
|
var lastImageDatesTags: [String]?
|
||||||
|
var lastImageT: Int?
|
||||||
|
var lastModifiedBy: String?
|
||||||
|
var lastModifiedT: Int?
|
||||||
|
var lc: String?
|
||||||
|
var link: String?
|
||||||
|
var linkDebugTags: [String]?
|
||||||
|
var manufacturingPlaces: String?
|
||||||
|
var manufacturingPlacesDebugTags: [String]?
|
||||||
|
var manufacturingPlacesTags: [String]?
|
||||||
|
var maxImgid: String?
|
||||||
|
var mineralsPrevTags: [String]?
|
||||||
|
var mineralsTags: [String]?
|
||||||
|
var miscTags: [String]?
|
||||||
|
var netWeightUnit: String?
|
||||||
|
var netWeightValue: String?
|
||||||
|
var nutritionDataPer: String?
|
||||||
|
var nutritionScoreWarningNoFruitsVegetablesNuts: Int?
|
||||||
|
var noNutritionData: String?
|
||||||
|
var novaGroup: String?
|
||||||
|
var novaGroups: String?
|
||||||
|
var novaGroupDebug: String?
|
||||||
|
var novaGroupTags: [String]?
|
||||||
|
var novaGroupsTags: [String]?
|
||||||
|
var nucleotidesPrevTags: [String]?
|
||||||
|
var nucleotidesTags: [String]?
|
||||||
|
var nutrientLevelsTags: [String]?
|
||||||
|
var nutritionData: String?
|
||||||
|
var nutritionDataPerDebugTags: [String]?
|
||||||
|
var nutritionDataPrepared: String?
|
||||||
|
var nutritionDataPreparedPer: String?
|
||||||
|
var nutritionGrades: String?
|
||||||
|
var nutritionScoreBeverage: Int?
|
||||||
|
var nutritionScoreDebug: String?
|
||||||
|
var nutritionScoreWarningNoFiber: Int?
|
||||||
|
var nutritionGradesTags: [String]?
|
||||||
|
var origins: String?
|
||||||
|
var originsDebugTags: [String]?
|
||||||
|
var originsTags: [String]?
|
||||||
|
var otherInformation: String?
|
||||||
|
var otherNutritionalSubstancesTags: [String]?
|
||||||
|
var packaging: String?
|
||||||
|
var packagingDebugTags: [String]?
|
||||||
|
var packagingTags: [String]?
|
||||||
|
var photographersTags: [String]?
|
||||||
|
var pnnsGroups1: String?
|
||||||
|
var pnnsGroups2: String?
|
||||||
|
var pnnsGroups1Tags: [String]?
|
||||||
|
var pnnsGroups2Tags: [String]?
|
||||||
|
var popularityKey: Int?
|
||||||
|
var producerVersionId: String?
|
||||||
|
var productName: String?
|
||||||
|
var productQuantity: String?
|
||||||
|
var purchasePlaces: String?
|
||||||
|
var purchasePlacesDebugTags: [String]?
|
||||||
|
var purchasePlacesTags: [String]?
|
||||||
|
var qualityTags: [String]?
|
||||||
|
var quantity: String?
|
||||||
|
var quantityDebugTags: [String]?
|
||||||
|
var recyclingInstructionsToDiscard: String?
|
||||||
|
var rev: Int?
|
||||||
|
var servingQuantity: String?
|
||||||
|
var servingSize: String?
|
||||||
|
var servingSizeDebugTags: [String]?
|
||||||
|
var sortkey: Int?
|
||||||
|
var states: String?
|
||||||
|
var statesHierarchy: [String]?
|
||||||
|
var statesTags: [String]?
|
||||||
|
var stores: String?
|
||||||
|
var storesDebugTags: [String]?
|
||||||
|
var storesTags: [String]?
|
||||||
|
var traces: String?
|
||||||
|
var tracesFromIngredients: String?
|
||||||
|
var tracesHierarchy: [String]?
|
||||||
|
var tracesDebugTags: [String]?
|
||||||
|
var tracesFromUser: String?
|
||||||
|
var tracesLc: String?
|
||||||
|
var tracesTags: [String]?
|
||||||
|
var unknownIngredientsN: Int?
|
||||||
|
var unknownNutrientsTags: [String]?
|
||||||
|
var updateKey: String?
|
||||||
|
var vitaminsPrevTags: [String]?
|
||||||
|
var vitaminsTags: [String]?
|
||||||
|
}
|
||||||
|
|
||||||
|
private enum CodingKeys: String, CodingKey {
|
||||||
|
case images
|
||||||
|
case ingredients
|
||||||
|
case languagesCodes = "languages_codes"
|
||||||
|
case nutrientLevels = "nutrient_levels"
|
||||||
|
case nutriments
|
||||||
|
case selectedImages = "selected_images"
|
||||||
|
case sources
|
||||||
|
case additivesN = "additives_n"
|
||||||
|
case additivesOldN = "additives_old_n"
|
||||||
|
case additivesOriginalTags = "additives_original_tags"
|
||||||
|
case additivesOldTags = "additives_old_tags"
|
||||||
|
case additivesPrevOriginalTags = "additives_prev_original_tags"
|
||||||
|
case additivesDebugTags = "additives_debug_tags"
|
||||||
|
case additivesTags = "additives_tags"
|
||||||
|
case allergens
|
||||||
|
case allergensFromIngredients = "allergens_from_ingredients"
|
||||||
|
case allergensFromUser = "allergens_from_user"
|
||||||
|
case allergensHierarchy = "allergens_hierarchy"
|
||||||
|
case allergensLc = "allergens_lc"
|
||||||
|
case allergensTags = "allergens_tags"
|
||||||
|
case aminoAcidsPrevTags = "amino_acids_prev_tags"
|
||||||
|
case aminoAcidsTags = "amino_acids_tags"
|
||||||
|
case brands
|
||||||
|
case brandsDebugTags = "brands_debug_tags"
|
||||||
|
case brandsTags = "brands_tags"
|
||||||
|
case carbonFootprintPercentOfKnownIngredients = "carbon_footprint_percent_of_known_ingredients"
|
||||||
|
case carbonFootprintFromKnownIngredientsDebug = "carbon_footprint_from_known_ingredients_debug"
|
||||||
|
case categories
|
||||||
|
case categoriesHierarchy = "categories_hierarchy"
|
||||||
|
case categoriesLc = "categories_lc"
|
||||||
|
case categoriesPropertiesTags = "categories_properties_tags"
|
||||||
|
case categoriesTags = "categories_tags"
|
||||||
|
case checkersTags = "checkers_tags"
|
||||||
|
case citiesTags = "cities_tags"
|
||||||
|
case code
|
||||||
|
case codesTags = "codes_tags"
|
||||||
|
case comparedToCategory = "compared_to_category"
|
||||||
|
case complete
|
||||||
|
case completedT = "completed_t"
|
||||||
|
case completeness
|
||||||
|
case conservationConditions = "conservation_conditions"
|
||||||
|
case countries
|
||||||
|
case countriesHierarchy = "countries_hierarchy"
|
||||||
|
case countriesLc = "countries_lc"
|
||||||
|
case countriesDebugTags = "countries_debug_tags"
|
||||||
|
case countriesTags = "countries_tags"
|
||||||
|
case correctorsTags = "correctors_tags"
|
||||||
|
case createdT = "created_t"
|
||||||
|
case creator
|
||||||
|
case dataQualityBugsTags = "data_quality_bugs_tags"
|
||||||
|
case dataQualityErrorsTags = "data_quality_errors_tags"
|
||||||
|
case dataQualityInfoTags = "data_quality_info_tags"
|
||||||
|
case dataQualityTags = "data_quality_tags"
|
||||||
|
case dataQualityWarningsTags = "data_quality_warnings_tags"
|
||||||
|
case dataSources = "data_sources"
|
||||||
|
case dataSourcesTags = "data_sources_tags"
|
||||||
|
case debugParamSortedLangs = "debug_param_sorted_langs"
|
||||||
|
case editorsTags = "editors_tags"
|
||||||
|
case embCodes = "emb_codes"
|
||||||
|
case embCodesDebugTags = "emb_codes_debug_tags"
|
||||||
|
case embCodesOrig = "emb_codes_orig"
|
||||||
|
case embCodesTags = "emb_codes_tags"
|
||||||
|
case entryDatesTags = "entry_dates_tags"
|
||||||
|
case expirationDate = "expiration_date"
|
||||||
|
case expirationDateDebugTags = "expiration_date_debug_tags"
|
||||||
|
case fruitsVegetablesNuts100GEstimate = "fruits-vegetables-nuts_100g_estimate"
|
||||||
|
case genericName
|
||||||
|
case id
|
||||||
|
case imageFrontSmallUrl = "image_front_small_url"
|
||||||
|
case imageFrontThumbUrl = "image_front_thumb_url"
|
||||||
|
case imageFrontUrl = "image_front_url"
|
||||||
|
case imageIngredientsUrl = "image_ingredients_url"
|
||||||
|
case imageIngredientsSmallUrl = "image_ingredients_small_url"
|
||||||
|
case imageIngredientsThumbUrl = "image_ingredients_thumb_url"
|
||||||
|
case imageNutritionSmallUrl = "image_nutrition_small_url"
|
||||||
|
case imageNutritionThumbUrl = "image_nutrition_thumb_url"
|
||||||
|
case imageNutritionUrl = "image_nutrition_url"
|
||||||
|
case imageSmallUrl = "image_small_url"
|
||||||
|
case imageThumbUrl = "image_thumb_url"
|
||||||
|
case imageUrl = "image_url"
|
||||||
|
case informersTags = "informers_tags"
|
||||||
|
case ingredientsAnalysisTags = "ingredients_analysis_tags"
|
||||||
|
case ingredientsDebug = "ingredients_debug"
|
||||||
|
case ingredientsFromOrThatMayBeFromPalmOilN = "ingredients_from_or_that_may_be_from_palm_oil_n"
|
||||||
|
case ingredientsFromPalmOilTags = "ingredients_from_palm_oil_tags"
|
||||||
|
case ingredientsFromPalmOilN = "ingredients_from_palm_oil_n"
|
||||||
|
case ingredientsHierarchy = "ingredients_hierarchy"
|
||||||
|
case ingredientsIdsDebug = "ingredients_ids_debug"
|
||||||
|
case ingredientsN = "ingredients_n"
|
||||||
|
case ingredientsNTags = "ingredients_n_tags"
|
||||||
|
case ingredientsOriginalTags = "ingredients_original_tags"
|
||||||
|
case ingredientsTags = "ingredients_tags"
|
||||||
|
case ingredientsText = "ingredients_text"
|
||||||
|
case ingredientsTextDebug = "ingredients_text_debug"
|
||||||
|
case ingredientsTextWithAllergens = "ingredients_text_with_allergens"
|
||||||
|
case ingredientsThatMayBeFromPalmOilN = "ingredients_that_may_be_from_palm_oil_n"
|
||||||
|
case ingredientsThatMayBeFromPalmOilTags = "ingredients_that_may_be_from_palm_oil_tags"
|
||||||
|
case interfaceVersionCreated = "interface_version_created"
|
||||||
|
case interfaceVersionModified = "interface_version_modified"
|
||||||
|
case keywords
|
||||||
|
case knownIngredientsN = "known_ingredients_n"
|
||||||
|
case labels
|
||||||
|
case labelsHierarchy = "labels_hierarchy"
|
||||||
|
case labelsLc = "labels_lc"
|
||||||
|
case labelsPrevHierarchy = "labels_prev_hierarchy"
|
||||||
|
case labelsPrevTags = "labels_prev_tags"
|
||||||
|
case labelsTags = "labels_tags"
|
||||||
|
case labelsDebugTags = "labels_debug_tags"
|
||||||
|
case lang
|
||||||
|
case langDebugTags = "lang_debug_tags"
|
||||||
|
case languagesHierarchy = "languages_hierarchy"
|
||||||
|
case languagesTags = "languages_tags"
|
||||||
|
case lastEditDatesTags = "last_edit_dates_tags"
|
||||||
|
case lastEditor = "last_editor"
|
||||||
|
case lastImageDatesTags = "last_image_dates_tags"
|
||||||
|
case lastImageT = "last_image_t"
|
||||||
|
case lastModifiedBy = "last_modified_by"
|
||||||
|
case lastModifiedT = "last_modified_t"
|
||||||
|
case lc
|
||||||
|
case link
|
||||||
|
case linkDebugTags = "link_debug_tags"
|
||||||
|
case manufacturingPlaces = "manufacturing_places"
|
||||||
|
case manufacturingPlacesDebugTags = "manufacturing_places_debug_tags"
|
||||||
|
case manufacturingPlacesTags = "manufacturing_places_tags"
|
||||||
|
case maxImgid = "max_imgid"
|
||||||
|
case mineralsPrevTags = "minerals_prev_tags"
|
||||||
|
case mineralsTags = "minerals_tags"
|
||||||
|
case miscTags = "misc_tags"
|
||||||
|
case netWeightUnit = "net_weight_unit"
|
||||||
|
case netWeightValue = "net_weight_value"
|
||||||
|
case nutritionDataPer = "nutrition_data_per"
|
||||||
|
case nutritionScoreWarningNoFruitsVegetablesNuts = "nutrition_score_warning_no_fruits_vegetables_nuts"
|
||||||
|
case noNutritionData = "no_nutrition_data"
|
||||||
|
case novaGroup = "nova_group"
|
||||||
|
case novaGroups = "nova_groups"
|
||||||
|
case novaGroupDebug = "nova_group_debug"
|
||||||
|
case novaGroupTags = "nova_group_tags"
|
||||||
|
case novaGroupsTags = "nova_groups_tags"
|
||||||
|
case nucleotidesPrevTags = "nucleotides_prev_tags"
|
||||||
|
case nucleotidesTags = "nucleotides_tags"
|
||||||
|
case nutrientLevelsTags = "nutrient_levels_tags"
|
||||||
|
case nutritionData = "nutrition_data"
|
||||||
|
case nutritionDataPerDebugTags = "nutrition_data_per_debug_tags"
|
||||||
|
case nutritionDataPrepared = "nutrition_data_prepared"
|
||||||
|
case nutritionDataPreparedPer = "nutrition_data_prepared_per"
|
||||||
|
case nutritionGrades = "nutrition_grades"
|
||||||
|
case nutritionScoreBeverage = "nutrition_score_beverage"
|
||||||
|
case nutritionScoreDebug = "nutrition_score_debug"
|
||||||
|
case nutritionScoreWarningNoFiber = "nutrition_score_warning_no_fiber"
|
||||||
|
case nutritionGradesTags = "nutrition_grades_tags"
|
||||||
|
case origins
|
||||||
|
case originsDebugTags = "origins_debug_tags"
|
||||||
|
case originsTags = "origins_tags"
|
||||||
|
case otherInformation = "other_information"
|
||||||
|
case otherNutritionalSubstancesTags = "other_nutritional_substances_tags"
|
||||||
|
case packaging
|
||||||
|
case packagingDebugTags = "packaging_debug_tags"
|
||||||
|
case packagingTags = "packaging_tags"
|
||||||
|
case photographersTags = "photographers_tags"
|
||||||
|
case pnnsGroups1 = "pnns_groups_1"
|
||||||
|
case pnnsGroups2 = "pnns_groups_2"
|
||||||
|
case pnnsGroups1Tags = "pnns_groups_1_tags"
|
||||||
|
case pnnsGroups2Tags = "pnns_groups_2_tags"
|
||||||
|
case popularityKey = "popularity_key"
|
||||||
|
case producerVersionId = "producer_version_id"
|
||||||
|
case productName = "product_name"
|
||||||
|
case productQuantity = "product_quantity"
|
||||||
|
case purchasePlaces = "purchase_places"
|
||||||
|
case purchasePlacesDebugTags = "purchase_places_debug_tags"
|
||||||
|
case purchasePlacesTags = "purchase_places_tags"
|
||||||
|
case qualityTags = "quality_tags"
|
||||||
|
case quantity
|
||||||
|
case quantityDebugTags = "quantity_debug_tags"
|
||||||
|
case recyclingInstructionsToDiscard = "recycling_instructions_to_discard"
|
||||||
|
case rev
|
||||||
|
case servingQuantity = "serving_quantity"
|
||||||
|
case servingSize = "serving_size"
|
||||||
|
case servingSizeDebugTags = "serving_size_debug_tags"
|
||||||
|
case sortkey
|
||||||
|
case states
|
||||||
|
case statesHierarchy = "states_hierarchy"
|
||||||
|
case statesTags = "states_tags"
|
||||||
|
case stores
|
||||||
|
case storesDebugTags = "stores_debug_tags"
|
||||||
|
case storesTags = "stores_tags"
|
||||||
|
case traces
|
||||||
|
case tracesFromIngredients = "traces_from_ingredients"
|
||||||
|
case tracesHierarchy = "traces_hierarchy"
|
||||||
|
case tracesDebugTags = "traces_debug_tags"
|
||||||
|
case tracesFromUser = "traces_from_user"
|
||||||
|
case tracesLc = "traces_lc"
|
||||||
|
case tracesTags = "traces_tags"
|
||||||
|
case unknownIngredientsN = "unknown_ingredients_n"
|
||||||
|
case unknownNutrientsTags = "unknown_nutrients_tags"
|
||||||
|
case updateKey = "update_key"
|
||||||
|
case vitaminsPrevTags = "vitamins_prev_tags"
|
||||||
|
case vitaminsTags = "vitamins_tags"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
enum OFFError: Error {
|
||||||
|
case invalidURL, invalidResponse
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user