1/* This Source Code Form is subject to the terms of the Mozilla Public 2 * License, v. 2.0. If a copy of the MPL was not distributed with this 3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 4 5#include "nsMacPreferencesReader.h" 6 7#include "js/JSON.h" 8#include "js/RootingAPI.h" 9#include "js/Value.h" 10#include "JSONWriter.h" 11 12NS_IMPL_ISUPPORTS(nsMacPreferencesReader, nsIMacPreferencesReader) 13 14using namespace mozilla; 15 16struct StringWriteFunc : public JSONWriteFunc { 17 nsAString& mString; 18 explicit StringWriteFunc(nsAString& aStr) : mString(aStr) {} 19 void Write(const Span<const char>& aStr) override { 20 mString.Append(NS_ConvertUTF8toUTF16(aStr.data(), aStr.size())); 21 } 22}; 23 24static void EvaluateDict(JSONWriter* aWriter, NSDictionary<NSString*, id>* aDict); 25 26static void EvaluateArray(JSONWriter* aWriter, NSArray* aArray) { 27 for (id elem in aArray) { 28 if ([elem isKindOfClass:[NSString class]]) { 29 aWriter->StringElement(MakeStringSpan([elem UTF8String])); 30 } else if ([elem isKindOfClass:[NSNumber class]]) { 31 aWriter->IntElement([elem longLongValue]); 32 } else if ([elem isKindOfClass:[NSArray class]]) { 33 aWriter->StartArrayElement(); 34 EvaluateArray(aWriter, elem); 35 aWriter->EndArray(); 36 } else if ([elem isKindOfClass:[NSDictionary class]]) { 37 aWriter->StartObjectElement(); 38 EvaluateDict(aWriter, elem); 39 aWriter->EndObject(); 40 } 41 } 42} 43 44static void EvaluateDict(JSONWriter* aWriter, NSDictionary<NSString*, id>* aDict) { 45 for (NSString* key in aDict) { 46 id value = aDict[key]; 47 if ([value isKindOfClass:[NSString class]]) { 48 aWriter->StringProperty(MakeStringSpan([key UTF8String]), MakeStringSpan([value UTF8String])); 49 } else if ([value isKindOfClass:[NSNumber class]]) { 50 aWriter->IntProperty(MakeStringSpan([key UTF8String]), [value longLongValue]); 51 } else if ([value isKindOfClass:[NSArray class]]) { 52 aWriter->StartArrayProperty(MakeStringSpan([key UTF8String])); 53 EvaluateArray(aWriter, value); 54 aWriter->EndArray(); 55 } else if ([value isKindOfClass:[NSDictionary class]]) { 56 aWriter->StartObjectProperty(MakeStringSpan([key UTF8String])); 57 EvaluateDict(aWriter, value); 58 aWriter->EndObject(); 59 } 60 } 61} 62 63NS_IMETHODIMP 64nsMacPreferencesReader::PoliciesEnabled(bool* aPoliciesEnabled) { 65 NSString* policiesEnabledStr = [NSString stringWithUTF8String:ENTERPRISE_POLICIES_ENABLED_KEY]; 66 *aPoliciesEnabled = [[NSUserDefaults standardUserDefaults] boolForKey:policiesEnabledStr] == YES; 67 return NS_OK; 68} 69 70NS_IMETHODIMP 71nsMacPreferencesReader::ReadPreferences(JSContext* aCx, JS::MutableHandle<JS::Value> aResult) { 72 nsAutoString jsonStr; 73 JSONWriter w(MakeUnique<StringWriteFunc>(jsonStr)); 74 w.Start(); 75 EvaluateDict(&w, [[NSUserDefaults standardUserDefaults] dictionaryRepresentation]); 76 w.End(); 77 78 auto json = static_cast<const char16_t*>(jsonStr.get()); 79 80 JS::RootedValue val(aCx); 81 MOZ_ALWAYS_TRUE(JS_ParseJSON(aCx, json, jsonStr.Length(), &val)); 82 83 aResult.set(val); 84 return NS_OK; 85} 86