<commit_before>/*
 * Copyright 2017 Coodly LLC
 *
 * 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

private let Heading = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
private let Normalizations = [
    "apiKey": "api-key",
    "entry": "time-entry",
    "inProgress": "in-progress",
    "durationInSeconds": "duration-in-seconds",
    "taskId": "task-id",
    "endTime": "end-time",
    "startTime": "start-time",
    "completedOn": "completed_on"
]
private let Filtered = ["id", "updatedAt", "createdAt"]
private let SendNullAsEmpty = ["completedOn"]

private extension DateFormatter {
    static let xmlDateFormatter: DateFormatter = {
        let formatter = DateFormatter()
        formatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ss'Z'"
        return formatter
    }()
}

internal struct XmlNode {
    let name: String
    let value: AnyObject
    
    func lines() -> [String] {
        var result = [String]()
        result.append("<\(name)>")
        
        if let string = value as? String {
            result.append(string.replacingOccurrences(of: "&", with: "&amp;"))
        } else if let nodes = value as? [XmlNode] {
            for node in nodes {
                result.append(contentsOf: node.lines())
            }
        }
        
        result.append("</\(name)>")
        return result
    }
}

internal protocol RequestBody {
    func asNodes() -> [XmlNode]
}

internal extension RequestBody {
    func asNodes() -> [XmlNode] {
        let mirror = Mirror(reflecting: self)
        
        var result = [XmlNode]()
        
        for child in mirror.children {            
            guard let name = child.label else {
                continue
            }
            
            if Filtered.contains(name) {<commit_msg>Used different & escape character<commit_after>/*
 * Copyright 2017 Coodly LLC
 *
 * 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

private let Heading = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
private let Normalizations = [
    "apiKey": "api-key",
    "entry": "time-entry",
    "inProgress": "in-progress",
    "durationInSeconds": "duration-in-seconds",
    "taskId": "task-id",
    "endTime": "end-time",
    "startTime": "start-time",
    "completedOn": "completed_on"
]
private let Filtered = ["id", "updatedAt", "createdAt"]
private let SendNullAsEmpty = ["completedOn"]

private extension DateFormatter {
    static let xmlDateFormatter: DateFormatter = {
        let formatter = DateFormatter()
        formatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ss'Z'"
        return formatter
    }()
}

internal struct XmlNode {
    let name: String
    let value: AnyObject
    
    func lines() -> [String] {
        var result = [String]()
        result.append("<\(name)>")
        
        if let string = value as? String {
            result.append(string.replacingOccurrences(of: "&", with: "&#038;"))
        } else if let nodes = value as? [XmlNode] {
            for node in nodes {
                result.append(contentsOf: node.lines())
            }
        }
        
        result.append("</\(name)>")
        return result
    }
}

internal protocol RequestBody {
    func asNodes() -> [XmlNode]
}

internal extension RequestBody {
    func asNodes() -> [XmlNode] {
        let mirror = Mirror(reflecting: self)
        
        var result = [XmlNode]()
        
        for child in mirror.children {            
            guard let name = child.label else {
                continue
            }
            
            if Filtered.contains(name) {
{'fraction_non_alphanumeric': 0.11759562841530055, 'fraction_numerical': 0.00546448087431694, 'mean_word_length': 2.4328582145536384, 'pattern_counts': {'":': 16, '<': 9, '<?xml version=': 2, '>': 15, 'https://': 0, 'lorem ipsum': 0, 'www.': 2, 'xml': 4}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '324656', 'n_tokens_mistral': 1297, 'n_tokens_neox': 1260, 'n_words': 415}