1 /* -*- Mode: C++; tab-width: 50; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /* vim:set ts=4 sw=4 sts=4: */
3 /* This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7 #include "nsHashPropertyBag.h"
9 #include "nsArrayEnumerator.h"
10 #include "nsIVariant.h"
11 #include "nsIProperty.h"
12 #include "nsVariant.h"
13 #include "mozilla/Attributes.h"
16 NS_NewHashPropertyBag(nsIWritablePropertyBag
** aResult
)
18 nsRefPtr
<nsHashPropertyBag
> hpb
= new nsHashPropertyBag();
24 * nsHashPropertyBag impl
27 NS_IMPL_ADDREF(nsHashPropertyBag
)
28 NS_IMPL_RELEASE(nsHashPropertyBag
)
29 NS_INTERFACE_MAP_BEGIN(nsHashPropertyBag
)
30 NS_INTERFACE_MAP_ENTRY(nsIWritablePropertyBag
)
31 NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsIPropertyBag
, nsIWritablePropertyBag
)
32 NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports
, nsIWritablePropertyBag
)
33 NS_INTERFACE_MAP_ENTRY(nsIPropertyBag2
)
34 NS_INTERFACE_MAP_ENTRY(nsIWritablePropertyBag2
)
38 nsHashPropertyBag::HasKey(const nsAString
& aName
, bool* aResult
)
40 *aResult
= mPropertyHash
.Get(aName
, nullptr);
45 nsHashPropertyBag::Get(const nsAString
& aName
, nsIVariant
** aResult
)
47 if (!mPropertyHash
.Get(aName
, aResult
)) {
55 nsHashPropertyBag::GetProperty(const nsAString
& aName
, nsIVariant
** aResult
)
57 bool isFound
= mPropertyHash
.Get(aName
, aResult
);
59 return NS_ERROR_FAILURE
;
66 nsHashPropertyBag::SetProperty(const nsAString
& aName
, nsIVariant
* aValue
)
68 if (NS_WARN_IF(!aValue
)) {
69 return NS_ERROR_INVALID_ARG
;
72 mPropertyHash
.Put(aName
, aValue
);
78 nsHashPropertyBag::DeleteProperty(const nsAString
& aName
)
80 // is it too much to ask for ns*Hashtable to return
81 // a boolean indicating whether RemoveEntry succeeded
83 bool isFound
= mPropertyHash
.Get(aName
, nullptr);
85 return NS_ERROR_FAILURE
;
89 mPropertyHash
.Remove(aName
);
96 // nsSimpleProperty class and impl; used for GetEnumerator
99 class nsSimpleProperty MOZ_FINAL
: public nsIProperty
101 ~nsSimpleProperty() {}
104 nsSimpleProperty(const nsAString
& aName
, nsIVariant
* aValue
)
114 nsCOMPtr
<nsIVariant
> mValue
;
117 NS_IMPL_ISUPPORTS(nsSimpleProperty
, nsIProperty
)
120 nsSimpleProperty::GetName(nsAString
& aName
)
127 nsSimpleProperty::GetValue(nsIVariant
** aValue
)
129 NS_IF_ADDREF(*aValue
= mValue
);
133 // end nsSimpleProperty
135 static PLDHashOperator
136 PropertyHashToArrayFunc(const nsAString
& aKey
,
140 nsIMutableArray
* propertyArray
= static_cast<nsIMutableArray
*>(aUserArg
);
141 nsSimpleProperty
* sprop
= new nsSimpleProperty(aKey
, aData
);
142 propertyArray
->AppendElement(sprop
, false);
143 return PL_DHASH_NEXT
;
148 nsHashPropertyBag::GetEnumerator(nsISimpleEnumerator
** aResult
)
150 nsCOMPtr
<nsIMutableArray
> propertyArray
= nsArray::Create();
151 if (!propertyArray
) {
152 return NS_ERROR_OUT_OF_MEMORY
;
155 mPropertyHash
.EnumerateRead(PropertyHashToArrayFunc
, propertyArray
.get());
157 return NS_NewArrayEnumerator(aResult
, propertyArray
);
160 #define IMPL_GETSETPROPERTY_AS(Name, Type) \
162 nsHashPropertyBag::GetPropertyAs ## Name (const nsAString & prop, Type *_retval) \
164 nsIVariant* v = mPropertyHash.GetWeak(prop); \
166 return NS_ERROR_NOT_AVAILABLE; \
167 return v->GetAs ## Name(_retval); \
171 nsHashPropertyBag::SetPropertyAs ## Name (const nsAString & prop, Type value) \
173 nsCOMPtr<nsIWritableVariant> var = new nsVariant(); \
174 var->SetAs ## Name(value); \
175 return SetProperty(prop, var); \
178 IMPL_GETSETPROPERTY_AS(Int32
, int32_t)
179 IMPL_GETSETPROPERTY_AS(Uint32
, uint32_t)
180 IMPL_GETSETPROPERTY_AS(Int64
, int64_t)
181 IMPL_GETSETPROPERTY_AS(Uint64
, uint64_t)
182 IMPL_GETSETPROPERTY_AS(Double
, double)
183 IMPL_GETSETPROPERTY_AS(Bool
, bool)
187 nsHashPropertyBag::GetPropertyAsAString(const nsAString
& aProp
,
190 nsIVariant
* v
= mPropertyHash
.GetWeak(aProp
);
192 return NS_ERROR_NOT_AVAILABLE
;
194 return v
->GetAsAString(aResult
);
198 nsHashPropertyBag::GetPropertyAsACString(const nsAString
& aProp
,
201 nsIVariant
* v
= mPropertyHash
.GetWeak(aProp
);
203 return NS_ERROR_NOT_AVAILABLE
;
205 return v
->GetAsACString(aResult
);
209 nsHashPropertyBag::GetPropertyAsAUTF8String(const nsAString
& aProp
,
212 nsIVariant
* v
= mPropertyHash
.GetWeak(aProp
);
214 return NS_ERROR_NOT_AVAILABLE
;
216 return v
->GetAsAUTF8String(aResult
);
220 nsHashPropertyBag::GetPropertyAsInterface(const nsAString
& aProp
,
224 nsIVariant
* v
= mPropertyHash
.GetWeak(aProp
);
226 return NS_ERROR_NOT_AVAILABLE
;
228 nsCOMPtr
<nsISupports
> val
;
229 nsresult rv
= v
->GetAsISupports(getter_AddRefs(val
));
234 // We have a value, but it's null
238 return val
->QueryInterface(aIID
, aResult
);
242 nsHashPropertyBag::SetPropertyAsAString(const nsAString
& aProp
,
243 const nsAString
& aValue
)
245 nsCOMPtr
<nsIWritableVariant
> var
= new nsVariant();
246 var
->SetAsAString(aValue
);
247 return SetProperty(aProp
, var
);
251 nsHashPropertyBag::SetPropertyAsACString(const nsAString
& aProp
,
252 const nsACString
& aValue
)
254 nsCOMPtr
<nsIWritableVariant
> var
= new nsVariant();
255 var
->SetAsACString(aValue
);
256 return SetProperty(aProp
, var
);
260 nsHashPropertyBag::SetPropertyAsAUTF8String(const nsAString
& aProp
,
261 const nsACString
& aValue
)
263 nsCOMPtr
<nsIWritableVariant
> var
= new nsVariant();
264 var
->SetAsAUTF8String(aValue
);
265 return SetProperty(aProp
, var
);
269 nsHashPropertyBag::SetPropertyAsInterface(const nsAString
& aProp
,
272 nsCOMPtr
<nsIWritableVariant
> var
= new nsVariant();
273 var
->SetAsISupports(aValue
);
274 return SetProperty(aProp
, var
);