Skip to content

Commit

Permalink
Unify Configuration Management (#241)
Browse files Browse the repository at this point in the history
Task/Issue URL: https://app.asana.com/0/72649045549333/1203797041821336/f
iOS PR: duckduckgo/iOS#1512
macOS PR: duckduckgo/macos-browser#990

Description:
Use common API and Configuration modules located in BSK for fetching privacy related assets.
Add payload validation.
  • Loading branch information
jaceklyp authored Mar 8, 2023
1 parent 3553b4e commit c10bf52
Show file tree
Hide file tree
Showing 42 changed files with 1,944 additions and 72 deletions.
42 changes: 37 additions & 5 deletions Package.swift
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,10 @@ let package = Package(
.library(name: "UserScript", targets: ["UserScript"]),
.library(name: "Crashes", targets: ["Crashes"]),
.library(name: "ContentBlocking", targets: ["ContentBlocking"]),
.library(name: "PrivacyDashboard", targets: ["PrivacyDashboard"]),
.library(name: "Configuration", targets: ["Configuration"]),
.library(name: "Networking", targets: ["Networking"]),
.library(name: "Navigation", targets: ["Navigation"]),
.library(name: "PrivacyDashboard", targets: ["PrivacyDashboard"])
],
dependencies: [
.package(name: "Autofill", url: "https://github.com/duckduckgo/duckduckgo-autofill.git", .exact("6.3.0")),
Expand Down Expand Up @@ -76,7 +78,7 @@ let package = Package(
name: "BloomFilter",
resources: [
.process("CMakeLists.txt")
]),
]),
.target(
name: "Crashes"
),
Expand Down Expand Up @@ -111,7 +113,7 @@ let package = Package(
]),
.target(
name: "UserScript"
),
),
.target(
name: "PrivacyDashboard",
dependencies: [
Expand All @@ -122,7 +124,24 @@ let package = Package(
.product(name: "PrivacyDashboardResources", package: "privacy-dashboard")
],
path: "Sources/PrivacyDashboard"
),
),
.target(
name: "Configuration",
dependencies: [
"Networking",
"BrowserServicesKit",
"Common"
]),
.target(
name: "Networking",
dependencies: [
"Common"
]),
.target(
name: "TestUtils",
dependencies: [
"Networking"
]),

// MARK: - Test targets
.testTarget(
Expand All @@ -139,6 +158,11 @@ let package = Package(
dependencies: [
"Common"
]),
.testTarget(
name: "NetworkingTests",
dependencies: [
"TestUtils"
]),
.testTarget(
name: "NavigationTests",
dependencies: [
Expand All @@ -160,7 +184,15 @@ let package = Package(
.testTarget(
name: "PersistenceTests",
dependencies: [
"Persistence"
"Persistence",
"TrackerRadarKit"
]
),
.testTarget(
name: "ConfigurationTests",
dependencies: [
"Configuration",
"TestUtils"
]
)
],
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,11 +21,8 @@ import Foundation
import Common

open class AppVersionProvider {
open func appVersion() -> String? {
return Bundle.main.releaseVersionNumber
}

public init() {
}
open func appVersion() -> String? { Bundle.main.releaseVersionNumber }
public init() { }

}
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,14 @@ public struct PrivacyConfigurationData {
public let trackerAllowlist: TrackerAllowlist
public let unprotectedTemporary: [ExceptionEntry]

public init(json: [String: Any]) {
public init(data: Data) throws {
guard let json = try JSONSerialization.jsonObject(with: data, options: []) as? [String: Any] else {
throw PrivacyConfigurationManager.ParsingError.dataMismatch
}
self = .init(json: json)
}

internal init(json: [String: Any]) {

if let tempListData = json[CodingKeys.unprotectedTemporary.rawValue] as? [[String: String]] {
unprotectedTemporary = tempListData.compactMap({ ExceptionEntry(json: $0) })
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ public protocol PrivacyConfigurationManaging: AnyObject {
var updatesPublisher: AnyPublisher<Void, Never> { get }
var privacyConfig: PrivacyConfiguration { get }

func reload(etag: String?, data: Data?) -> PrivacyConfigurationManager.ReloadResult
@discardableResult func reload(etag: String?, data: Data?) -> PrivacyConfigurationManager.ReloadResult
}

public class PrivacyConfigurationManager: PrivacyConfigurationManaging {
Expand Down Expand Up @@ -85,8 +85,7 @@ public class PrivacyConfigurationManager: PrivacyConfigurationManaging {
data = embedded
} else {
let jsonData = embeddedDataProvider.embeddedData
let json = try? JSONSerialization.jsonObject(with: jsonData, options: []) as? [String: Any]
let configData = PrivacyConfigurationData(json: json!)
let configData = try! PrivacyConfigurationData(data: jsonData)
_embeddedConfigData = (jsonData, configData, embeddedDataProvider.embeddedDataEtag)
data = _embeddedConfigData
}
Expand Down Expand Up @@ -145,12 +144,8 @@ public class PrivacyConfigurationManager: PrivacyConfigurationManaging {

do {
// This might fail if the downloaded data is corrupt or format has changed unexpectedly
if let json = try JSONSerialization.jsonObject(with: data, options: []) as? [String: Any] {
let configData = PrivacyConfigurationData(json: json)
fetchedConfigData = (data, configData, etag)
} else {
throw ParsingError.dataMismatch
}
let configData = try PrivacyConfigurationData(data: data)
fetchedConfigData = (data, configData, etag)
} catch {
errorReporting?.fire(.privacyConfigurationParseFailed, error: error)
fetchedConfigData = nil
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
//

import Foundation
import Common

public struct AppAttributeMatcher: AttributeMatcher {

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,14 +18,15 @@
//

import Foundation
import Common

public struct DeviceAttributeMatcher: AttributeMatcher {

let osVersion: String
let localeIdentifier: String

public init() {
self.init(osVersion: AppVersion.shared.osVersion(), locale: Locale.current.identifier)
self.init(osVersion: AppVersion.shared.osVersion, locale: Locale.current.identifier)
}

public init(osVersion: String, locale: String) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
//

import Foundation
import Common

// swiftlint:disable file_length

Expand Down Expand Up @@ -65,7 +66,7 @@ struct LocaleMatchingAttribute: MatchingAttribute, Equatable {

struct OSMatchingAttribute: MatchingAttribute, Equatable {
var min: String = MatchingAttributeDefaults.stringDefaultValue
var max: String = AppVersion.shared.osVersion()
var max: String = AppVersion.shared.osVersion
var value: String = MatchingAttributeDefaults.stringDefaultValue
var fallback: Bool?

Expand All @@ -87,7 +88,7 @@ struct OSMatchingAttribute: MatchingAttribute, Equatable {
}

init(min: String = MatchingAttributeDefaults.stringDefaultValue,
max: String = AppVersion.shared.osVersion(),
max: String = AppVersion.shared.osVersion,
value: String = MatchingAttributeDefaults.stringDefaultValue,
fallback: Bool?) {
self.min = min
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,17 +18,9 @@
//

import Foundation
import Common

public struct AppVersion {

public struct Keys {
static let name = kCFBundleNameKey as String
static let identifier = kCFBundleIdentifierKey as String
static let buildNumber = kCFBundleVersionKey as String
static let versionNumber = "CFBundleShortVersionString"
}

public static let shared = AppVersion()

private let bundle: InfoBundle
Expand All @@ -38,23 +30,23 @@ public struct AppVersion {
}

public var name: String {
return bundle.object(forInfoDictionaryKey: Keys.name) as? String ?? ""
return bundle.object(forInfoDictionaryKey: Bundle.Key.name) as? String ?? ""
}

public var identifier: String {
return bundle.object(forInfoDictionaryKey: Keys.identifier) as? String ?? ""
return bundle.object(forInfoDictionaryKey: Bundle.Key.identifier) as? String ?? ""
}

public var majorVersionNumber: String {
return String(versionNumber.split(separator: ".").first ?? "")
}

public var versionNumber: String {
return bundle.object(forInfoDictionaryKey: Keys.versionNumber) as? String ?? ""
return bundle.object(forInfoDictionaryKey: Bundle.Key.versionNumber) as? String ?? ""
}

public var buildNumber: String {
return bundle.object(forInfoDictionaryKey: Keys.buildNumber) as? String ?? ""
return bundle.object(forInfoDictionaryKey: Bundle.Key.buildNumber) as? String ?? ""
}

public var versionAndBuildNumber: String {
Expand All @@ -65,8 +57,9 @@ public struct AppVersion {
return "\(name) \(versionAndBuildNumber)"
}

func osVersion() -> String {
public var osVersion: String {
let os = ProcessInfo().operatingSystemVersion
return "\(os.majorVersion).\(os.minorVersion).\(os.patchVersion)"
}

}
19 changes: 10 additions & 9 deletions Sources/Common/Extensions/BundleExtension.swift
Original file line number Diff line number Diff line change
Expand Up @@ -20,18 +20,19 @@
import Foundation

extension Bundle {

struct Keys {

enum Key {

static let name = kCFBundleNameKey as String
static let versionNumber = "CFBundleShortVersionString"
}
static let identifier = kCFBundleIdentifierKey as String
static let buildNumber = kCFBundleVersionKey as String
static let versionNumber = "CFBundleShortVersionString"
static let displayName = "CFBundleDisplayName"

public var releaseVersionNumber: String? {
return infoDictionary?[Keys.versionNumber] as? String
}

public var name: String? {
object(forInfoDictionaryKey: Keys.name) as? String
}
public var releaseVersionNumber: String? { infoDictionary?[Key.versionNumber] as? String }
public var displayName: String? { object(forInfoDictionaryKey: Key.displayName) as? String ?? name }
public var name: String? { object(forInfoDictionaryKey: Key.name) as? String }

}
8 changes: 4 additions & 4 deletions Sources/Common/Extensions/URLExtension.swift
Original file line number Diff line number Diff line change
Expand Up @@ -268,10 +268,10 @@ extension URL {
}

// MARK: - Parameters

public func appendingParameters<C: Collection>(_ parameters: C, allowedReservedCharacters: CharacterSet? = nil) -> URL
where C.Element == (key: String, value: String) {

public func appendingParameters<QueryParams: Collection>(_ parameters: QueryParams, allowedReservedCharacters: CharacterSet? = nil) -> URL
where QueryParams.Element == (key: String, value: String) {
return parameters.reduce(self) { partialResult, parameter in
partialResult.appendingParameter(
name: parameter.key,
Expand Down
5 changes: 3 additions & 2 deletions Sources/Common/InfoBundle.swift
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,9 @@
import Foundation

public protocol InfoBundle {

func object(forInfoDictionaryKey key: String) -> Any?

}

extension Bundle: InfoBundle {
}
extension Bundle: InfoBundle { }
48 changes: 48 additions & 0 deletions Sources/Configuration/Configuration.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
//
// Configuration.swift
// DuckDuckGo
//
// Copyright © 2023 DuckDuckGo. All rights reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//

import Foundation

public protocol ConfigurationURLProviding {

func url(for configuration: Configuration) -> URL

}

public enum Configuration: String, CaseIterable, Sendable {

case bloomFilterBinary
case bloomFilterSpec
case bloomFilterExcludedDomains
case privacyConfiguration
case surrogates
case trackerDataSet
case FBConfig

private static var urlProvider: ConfigurationURLProviding?
public static func setURLProvider(_ urlProvider: ConfigurationURLProviding) {
self.urlProvider = urlProvider
}

var url: URL {
guard let urlProvider = Self.urlProvider else { fatalError("Please set the urlProvider before accessing url.") }
return urlProvider.url(for: self)
}

}
Loading

0 comments on commit c10bf52

Please sign in to comment.