Checking for multiple postalAddresses for the contact swift 5 - ios13

I finally got time to go back and work on this. The code below pulls the address labels and IDs. The IDs are fine. The problem is when I print theAddressLabel it give me this:
_$!<Home>!$_
Is this normal or is there something in my code I can change to fix it? All I want it to contain is "Home". Do I need to strip-out the first and last four characters before it goes into the array?
func getContactFromID_Ouote2(contactID: String)
{
struct contactAddresses
{
var theLabel: String
var theID: String
}
let store = CNContactStore()
var theName = CNContact()
var theTypes = [contactAddresses]()
var theAddressID: String = ""
var theAddressLabel: String = ""
let theKeys = [CNContactPostalAddressesKey] as [CNKeyDescriptor]
do {
theName = try store.unifiedContact(withIdentifier: contactID, keysToFetch: theKeys)
let postalAddress = theName.postalAddresses
postalAddress.forEach { (mailAddress) in
theTypes.append(contactAddresses(theLabel: mailAddress.label!, theID: mailAddress.identifier))
}
for theItem in theTypes
{
theAddressLabel = theItem.theLabel
theAddressID = theItem.theID
print(theAddressLabel)
print(theAddressID)
}
} catch {
print("Fetching contact data failed: \(error)")
}
How do I check to see if there are multiple postalAddresses (home, work, etc.) for a contact?
If there are multiple postalAddresses then my plan is to present an alert to allow the user to pick the one to use. Presenting the alert isn't a problem, I just need help with getting the addresses.
Thanks in advance.
func getContactFromID_Ouote(contactID: String)
{
let store = CNContactStore()
var theName = CNContact()
let theKeys = [CNContactNamePrefixKey,
CNContactGivenNameKey,
CNContactFamilyNameKey,
CNContactNameSuffixKey,
CNContactOrganizationNameKey,
CNContactPostalAddressesKey,
CNContactFormatter.descriptorForRequiredKeys(for: .fullName)] as! [CNKeyDescriptor]
do {
theName = try store.unifiedContact(withIdentifier: contactID, keysToFetch: theKeys)
contactName = CNContactFormatter.string(from: theName, style: .fullName)!
contactPrefix = theName.namePrefix
contactFirst = theName.givenName
contactLast = theName.familyName
companyName = theName.organizationName == "" ? "" : theName.organizationName
} catch {
print("Fetching contact data failed: \(error)")
}
if let firstPostalAddress = (theName.postalAddresses.first),
let labelValuePair = firstPostalAddress.value(forKey: "labelValuePair") as? AnyObject,
let finalPostalAddress = labelValuePair.value(forKey: "value") as? CNPostalAddress
{
mailAddress = CNPostalAddressFormatter.string(from: finalPostalAddress, style: .mailingAddress)
}
}

Your can use below code for fetch multiple mailingAddresses.
func getContactFromID_Ouote(contactID: String)
{
let store = CNContactStore()
var theName = CNContact()
let theKeys = [CNContactEmailAddressesKey] as [CNKeyDescriptor]
do {
theName = try store.unifiedContact(withIdentifier: contactID, keysToFetch: theKeys)
let emailAddress = theName.emailAddresses
emailAddress.forEach { (mailAddress) in
print("Your Mail Address is :- ",mailAddress.value)
print("Your Mail Type :- ",mailAddress.label)
}
} catch {
print("Fetching contact data failed: \(error)")
}
}

Related

vulnerability from security team in forget password controller in asp .net

I have a controller form application and the security team they said there is a vulnerability you can put any user_id fom postman inside the controller like this
ForgotPassword/user_id
how I can remove this vulnerability check the code below:
[HttpPost]
[ValidateAntiForgeryToken]
public JsonResult ForgotPassword(string emailId)
{
var helper = new Helper.Helper();
List<SqlParameter> args = new List<SqlParameter>();
args.Add(new SqlParameter("#Pin_email_id", emailId));
var req_resp = new Dictionary<string, object>();
try
{
using (DataSet dataset = helper.ExecuteSqlQuery("Web_Forgot_Password", args))
{
if (dataset != null && dataset.Tables.Count > 0 && dataset.Tables[0].Rows.Count > 0)
{
if (dataset.Tables[0].Rows[0]["Status"].ToString() == "Success")
{
req_resp["status"] = true;
req_resp["message"] = dataset.Tables[0].Rows[0]["Description"].ToString();
req_resp["code"] = dataset.Tables[0].Rows[0]["Code"].ToString();
string password = dataset.Tables[0].Rows[0]["user_password"].ToString();
SendForgotMail(emailId, dataset.Tables[0].Rows[0]["user_name"].ToString(), helper.Decrypt(password), dataset.Tables[0].Rows[0]["employee"].ToString());
return Json(req_resp);
}
else
{
req_resp["status"] = false;
req_resp["message"] = dataset.Tables[0].Rows[0]["Description"].ToString();
req_resp["code"] = dataset.Tables[0].Rows[0]["Code"].ToString();
return Json(req_resp);
}
}
else
{
req_resp["status"] = false;
req_resp["message"] = "Request Failed";
req_resp["code"] = "1005";
return Json(req_resp);
}
}
}
catch
{
var response = new
{
status = false,
message = "Request failed",
code = "1005"
};
return Json(response);
}
}
Well normally you store only password hashes in your database, which are not decryptable. Watching helper.Decrypt(password) in your code and sending the original password as a plain text in email is something painful. Normally I would just send a password reset link which can be used only once.
I checked the SqlParemater docs, it is added as a String value the way you use it, so it is not SQL injectable. Without the exact SQL I cannot tell much. I think they meant that it is SQL injectable, but then they should send evidence at least.

how we can return a status code for the serialized JSON object using Newtonsoft.net

I have this Action method which act as an API end point inside our ASP.NET MVC-5, where it search for a username and return the username Phone number and Department from Active Directory (we are serializing the object using Newtonsoft.net):-
public ActionResult UsersInfo2()
{
DomainContext result = new DomainContext();
try
{
// create LDAP connection object
DirectoryEntry myLdapConnection = createDirectoryEntry();
string ADServerName = System.Web.Configuration.WebConfigurationManager.AppSettings["ADServerName"];
string ADusername = System.Web.Configuration.WebConfigurationManager.AppSettings["ADUserName"];
string ADpassword = System.Web.Configuration.WebConfigurationManager.AppSettings["ADPassword"];
using (var context = new DirectoryEntry("LDAP://mydomain.com:389/DC=mydomain,DC=com", ADusername, ADpassword))
using (var search = new DirectorySearcher(context))
{
// create search object which operates on LDAP connection object
// and set search object to only find the user specified
// DirectorySearcher search = new DirectorySearcher(myLdapConnection);
// search.PropertiesToLoad.Add("telephoneNumber");
search.Filter = "(&(objectClass=user)(sAMAccountName=test.test))";
SearchResult r = search.FindOne();
ResultPropertyCollection fields = r.Properties;
foreach (String ldapField in fields.PropertyNames)
{
// cycle through objects in each field e.g. group membership
// (for many fields there will only be one object such as name)
string temp;
// foreach (Object myCollection in fields[ldapField])
// {
// temp = String.Format("{0,-20} : {1}",
// ldapField, myCollection.ToString());
if (ldapField.ToLower() == "telephonenumber")
{
foreach (Object myCollection in fields[ldapField])
{
result.Telephone = myCollection.ToString();
}
}
else if (ldapField.ToLower() == "department")
{
foreach (Object myCollection in fields[ldapField])
{
result.Department = myCollection.ToString();
}
}
// }
}
string output = JsonConvert.SerializeObject(result);
return Json(output,JsonRequestBehavior.AllowGet);
}
}
catch (Exception e)
{
Console.WriteLine("Exception caught:\n\n" + e.ToString());
}
return View(result);
}
now the return JSON will be as follow:-
"\"DisplayName\":null,\"Telephone\":\"123123\",\"Department\":\"IT\",\"Name\":null,\"SamAccountName\":null,\"DistinguishedName\":null,\"UserPrincipalName\":null}"
but in our case we need to return a status code beside the return json data. for example inccase there is an exception we need to return an error code,also if we are able to get the user's info we need to pass succes code 200, and so on.. so how we can achieve this?
you can try something like this
var statusCode=200;
string output = JsonConvert.SerializeObject( new { result = result, StatusCode = statusCode);
but nobody usually do this. When users call API they can check status code that HTTP Client returns, using code like this
var response = await client.GetAsync(api);
//or
var response = await client.PutAsJsonAsync(api, data);
var statusCode = response.StatusCode.ToString();
//or usually
if (response.IsSuccessStatusCode) {...}
else {...}

Why does assigning a JArray to a var fail when I call JsonConvert.DeserializeObject()?

On this line of code:
var arr = JsonConvert.DeserializeObject<JArray>(s);
...I am getting, "Unable to cast object of type 'Newtonsoft.Json.Linq.JObject' to type 'Newtonsoft.Json.Linq.JArray'."
I changed that line to this:
JArray arr = JsonConvert.DeserializeObject<JArray>(s);
...and got the same err msg.
I changed it to this:
var arr = JsonConvert.DeserializeObject<JObject>(s);
...and it wouldn't even compile.
The value of what has been read by the call (in string s) at this point is:
{"id":347745,"results":[{"iso_3166_1":"US","release_dates":[{"certification":"","iso_639_1":"","note":"","release_date":"1936-12-12T00:00:00.000Z","type":3}]}]}
All I want from it is the value for "certification"; In this case, the certification value is an empty string ("certification":"")
In context, the code is:
. . .
try
{
var webRequest = (HttpWebRequest)WebRequest.Create(RESTStringToGetMPAARatingForMovieId);
webRequest.Method = "GET";
var webResponse = (HttpWebResponse)webRequest.GetResponse();
if ((webResponse.StatusCode == HttpStatusCode.OK) && (webResponse.ContentLength > 0))
{
StreamReader streamReader = new StreamReader(webResponse.GetResponseStream());
string s = streamReader.ReadToEnd();
var arr = JsonConvert.DeserializeObject<JArray>(s);
//JArray arr = JsonConvert.DeserializeObject<JArray>(s);
//var arr = JsonConvert.DeserializeObject<JObject>(s);
foreach (JObject obj in arr)
{
_currentMPAARating = (string)obj["certification"];
. . .
}
}
else
{
MessageBox.Show(string.Format("Status code == {0}, Content length == {1}",
webResponse.StatusCode, webResponse.ContentLength));
}
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
Your JSON is not an array, it is an object which contains an array (results). But it's actually more complicated than that: the certification string you seek is nested even further down inside a second release_dates array.
If you take your JSON and reformat it using a JSON validator/beautifier, it should become more clear:
{
"id": 347745,
"results": [
{
"iso_3166_1": "US",
"release_dates": [
{
"certification": "",
"iso_639_1": "",
"note": "",
"release_date": "1936-12-12T00:00:00Z",
"type": 3
}
]
}
]
}
So to get the data you are looking for using regular foreach loops, you would need code like this:
var obj = JsonConvert.DeserializeObject<JObject>(s);
var resultArr = (JArray)obj["results"];
foreach (JObject resultObj in resultArr)
{
var releaseDatesArr = (JArray)resultObj["release_dates"];
foreach (JObject releaseDateObj in releaseDatesArr)
{
_currentMPAARating = (string)releaseDateObj["certification"];
// ...
}
}
Fiddle: https://dotnetfiddle.net/SMzQTw
If all you need is the one item, here's a shortcut. Use the SelectToken method with the recursive descent operator (..) like this:
var obj = JsonConvert.DeserializeObject<JObject>(s);
_currentMPAARating = (string)obj.SelectToken("..certification");
Fiddle: https://dotnetfiddle.net/S1ScLO
But note the above will only return the first match. If you are expecting multiple certifications, you can use SelectTokens (plural) instead:
var obj = JsonConvert.DeserializeObject<JObject>(s);
var ratings = obj.SelectTokens("..certification").Select(t => (string)t).ToList();
Fiddle: https://dotnetfiddle.net/zyjNnJ

Getting error when a method is made for post request

When made I post request is made its giving internal server. Is the implementation of Flurl is fine or I am doing something wrong.
try
{
Models.PaymentPost paymentPost = new Models.PaymentPost();
paymentPost.Parts = new Models.Parts();
paymentPost.Parts.Specification = new Models.Specification();
paymentPost.Parts.Specification.CharacteristicsValue = new List<Models.CharacteristicsValue>();
paymentPost.Parts.Specification.CharacteristicsValue.Add(new Models.CharacteristicsValue { CharacteristicName = "Amount", Value = amount });
paymentPost.Parts.Specification.CharacteristicsValue.Add(new Models.CharacteristicsValue { CharacteristicName = "AccountReference", Value = accountId });
foreach (var item in extraParameters)
{
paymentPost.Parts.Specification.CharacteristicsValue.Add(new Models.CharacteristicsValue {
CharacteristicName = item.Key, Value = item.Value });
}
var paymentInJson = JsonConvert.SerializeObject(paymentPost);
var selfCareUrl = "http://svdt5kubmas01.safari/auth/processPaymentAPI/v1/processPayment";
var fUrl = new Flurl.Url(selfCareUrl);
fUrl.WithBasicAuth("***", "********");
fUrl.WithHeader("X-Source-System", "POS");
fUrl.WithHeader("X-Route-ID", "STKPush");
fUrl.WithHeader("Content-Type", "application/json");
fUrl.WithHeader("X-Correlation-ConversationID", "87646eaa-2605-405e-967c-56e8002b5");
fUrl.WithHeader("X-Route-Timestamp", "150935");
fUrl.WithHeader("X-Source-Operator", " ");
var response = await clientFactory.Get(fUrl).Request().PostJsonAsync(paymentInJson).ReceiveJson<IEnumerable<IF.Models.PaymentPost>>();
return response;
}
catch (FlurlHttpException ex)
{
dynamic d = ex.GetResponseJsonAsync();
//string s = ex.GetResponseStringAsync();
return d;
}
You don't need to do this:
var paymentInJson = JsonConvert.SerializeObject(paymentPost);
PostJsonAsync just takes a regular object and serializes it to JSON for you. Here you're effectively double-serializing it and the server is probably confused by that format.
You're also doing a lot of other things that Flurl can do for you, such as creating those Url and client objects explicitly. Although that's not causing errors, this is how Flurl is typically used:
var response = await selfCareUrl
.WithBasicAuth(...)
.WithHeader(...)
...
.PostJsonAsync(paymentPost)
.ReceiveJson<List<IF.Models.PaymentPost>>();

how to add contacts in telegram-cli by using vcard?

im trying to add my contacts in telegram-cli by using vcard. but when i use this command:
import_card <card>
nothing happen! it just goes to next line without any error and no contact added.
my vcard is VERSION:2.1
how can i improt my contacts to my telegram account by using vcard?
Install-Package TLSharp
client = new TelegramClient(apiId, apiHash);
await client.ConnectAsync();
var phoneContact = new TLInputPhoneContact() { phone = "", first_name = "", last_name = "" };
var contacts = new List<TLInputPhoneContact>() { phoneContact };
var req = new TeleSharp.TL.Contacts.TLRequestImportContacts() { contacts = new TLVector<TLInputPhoneContact>() { lists = contacts } };
var rrr= await client.SendRequestAsync<TeleSharp.TL.Contacts.TLImportedContacts>(req);
private async Task<bool> ImportContact(string _phone , string _first_name , string _last_name)
{
//https://github.com/sochix/TLSharp/issues/243
var phoneContact = new TLInputPhoneContact() { phone = _phone, first_name = _first_name, last_name = _last_name };
var contacts = new List<TLInputPhoneContact>() { phoneContact };
var req = new TLRequestImportContacts() { contacts = new TLVector<TLInputPhoneContact>() { lists = contacts } };
TLImportedContacts result = await client.SendRequestAsync<TLImportedContacts>(req);
if (result.users.lists.Count > 0)
return true;
else return false;
}

Resources