SalesForce SOQL MALFORMED_QUERY - salesforce

Why is this SOQL query returning MALFORMED_QUERY: unexpected token: on
Select id FROM account
where id = '0012000000I7MkRAAV' or id = '0012000000I7MkRAAV'
and id = '0012000000I7MkRAAV'
Changing "and" to "or" returns the result just fine:
Select id FROM account
where id = '0012000000I7MkRAAV' or id = '0012000000I7MkRAAV'
or id = '0012000000I7MkRAAV'
I am executing the query in Force explorer.

You need to group your and/or's so that its not ambiguous, e.g.
Select id FROM account where id = '0012000000I7MkRAAV' or (id = '0012000000I7MkRAAV' and id = '0012000000I7MkRAAV')

The problem is that one account record can't has two ids in the same time. One object record has just one Id. In this query you can use only OR statement

Related

How can i create an object in Salesforce that automatically populates any dependent objects?

If i need to creat an Order , I need to first creat an Account and then assign the AccountId to the Order, like the following
Account a = new Account();
a.Name = 'Test';
insert a;
Order order = new Order(
AccountId = a.Id,
Status='Draft',
EffectiveDate = Date.today());
insert order;
Is there a way I can simply create an Order and the dependent objects will be created or is there a way to get what Sobject field the AccountId of the order is related to ?
There is no way for Salesforce to automatically create the dependent sObjects, they will have to be inserted.
Regarding your second question (retrieving the type of sObject from the field name) you can check out this question on Salesforce StackExchange. Below is that code being ran for the AccountId field on the Order object:

Get Contact Emails of Currently Active Account as List

Given: A Salesforce user is viewing an account page.
Desired Output: All Emails of Contacts related to the Account currently viewed as a List object.
My code:
SELECT Email FROM Contact WHERE Id IN (SELECT ContactId FROM AccountContactRelation WHERE AccountId = ApexPages.CurrentPage.getParameters().get('id'))
This does not retrieve any results. When using a fixed number instead of ApexPages.CurrentPage.getParameters().get('id'), the Emails are correctly returned.
I'm sort of new to Apex. Could anyone point out what I am doing wrong?
To achieve the desired output you need to use SOQL variable injection.
You can do this by creating a variable first and then referencing the variable inside the SOQL using : and the variable name:
String theAccountId = ApexPages.CurrentPage.getParameters().get('id');
List<Contact> theContacts = [SELECT Email FROM Contact WHERE Id IN (SELECT ContactId FROM AccountContactRelation WHERE AccountId = :theAccountId)];
You can use a static query with a bind variable to retrieve the correct results.
Additionally, the Contact object contains an AccountId field of its own. Therefore, depending on your setup, you may be able to eliminate your subquery. You may also want to filter out Email fields that are empty, since Email is not a required field.
The complete result could look something like this:
String accountId = ApexPages.CurrentPage.getParameters().get('id');
List<Contact> accountContactsEmailList = [
SELECT
Email
FROM
Contact
WHERE
Email != ''
AND AccountId = :accountId
];
for (Contact contact : accountContactsEmailList) {
System.debug(contact.Email);
}

SOQL Account query for custom object related to opportunities

I'm trying to figure out how to query a custom object that is related to opportunities.
The object name is McaApp__Offer__c
The lookup field for that object is McaApp__Opportunity__c (master-detail)
This is what I have, but I'mk missing something as this object is not related to accounts, what do I need to change?
SELECT id, Name,
(
Select Id, Name From Opportunities ORDER BY Id DESC LIMIT 1
),
(
SELECT McaApp__Funder__c, McaApp__Status__c FROM McaApp__Offers__r WHERE McaApp__Opportunity__c = 'oppidxxx'
)
FROM Account
WHERE id = 'acctidxxx'
You can't query McaApp__Offer__c from within Account as there is no direct relationship. Account < Opportunity < McaApp__Offer__c this is how it realted.
SOQL statements cannot query aggregate relationships more than 1 level
away from the root entity object.
You can do like this.
SELECT Id, Name, AccountId,
(SELECT McaApp__Funder__c, McaApp__Status__c
FROM McaApp__Offers__r)
FROM Opportunity
WHERE AccountId = 'acctidxxx'
LIMIT 1

Salesforce SOQL Filter by child relationship

I have the following simple query which shows I can access the field I want to filter by:
SELECT Id, Name, (SELECT HC4__IsSearchableExternally__c FROM Contacts)
FROM Account
However, what I really want to do is return only the Id and Name properties for Accounts that have at least one Contact where HC4__IsSearchableExternally__c is true. Is this possible to do with a Salesforce query?
Basically, I want to do something like the following (nonfunctional query):
SELECT Id, Name
FROM Account
WHERE (SELECT COUNT(Id) FROM Contacts WHERE HC4__IsSearchableExternally__c = true) > 0
Thanks for any help you can provide!
You can do this with a semi-join, e.g:
select id, name from account
where id in (select accountId from contact where HC4__IsSearchableExternally__c = true)

SalesForce: Query objects a user has read permission for

How can I Query all Accounts a given user has read permission for?
I tried the following but, returned the error "semi join sub selects can only query id fields, cannot use: 'RecordId'"
User u = new User();
Account[] account = [SELECT Name FROM Account a
WHERE Id IN
(
SELECT RecordId
FROM UserRecordAccess
WHERE RecordId = :a.Id
AND UserId = :u
AND HasReadAccess = true
)
];
The code is being executed as part of a scheduled batch job run as system so use of "with sharing" is not applicable.
Thanks
The salesforce documentation says that RecordID is a picklist field which seems odd. If it is a picklist field that might explain why it does not work in a subquery.
You could try building a set of RecordIDs first and then using this to filter the Account query.
Set<ID> sRecordIDs = [SELECT RecordID FROM UserRecordAccess WHERE UserId = :u AND HasReadAccess = True];
Account[] accs =[SELECT ID,Name FROM Account WHERE Id in :sRecordIDs];
This might fall over governor limits if the number of records in UserRecordAccess is high.
If you are only looking to do this for Account you could try this:
User u = new User();
list<Account> accs = [select Id, Name from Account where Id in (select AccountId from AccountShare where UserOrGroupId = :u.Id) or OwnerId = :u.Id];
That should give you all of the account records that the user has access to or owns. In the general case each sObject has its own 'Share' sObject that represents visibility against it, unless it is degenerate in some way (i.e. it is the detail in a master-detail).

Resources