Регистрация  |  Вход

Поле, хранящее кол-во связанных, но не дочерних записей. Только тригер?

Всем привет!

еще одно простая, но насущная задачка.

На записи должно быть поле хранящее кол-во связанных через лук-ап, но не дочерних записей.

вроде задача выглядит просто, но решить получается только через тригер.

причем тригер нужно ставить не на тот объект на котором стоит это "sum-up" поле, а на объект связанных записей, так получается?

но можно ли задачу решить по другому: а зачем это поле вообще нужно?

дело в том что на головной записи хранится цена (100) общая (суммарная) для всех связанных записей. А на каждой связанной записи есть формульное поле ("Усредненная цена на единицу"), которое должно вытянуть из головной записи эту цену и поделить на кол-во всех записей привязнных в головной записи. Для этого и создаем поле с кол-вом связанных записей на головной записи. Но может кол-во связанных записей можно как-то посчитать в формуле на самой связанной записи. не думаю.

спасибо

Всем привет!

еще одно простая, но насущная задачка.

На записи должно быть поле хранящее  кол-во связанных через лук-ап, но не дочерних записей.

вроде задача выглядит просто, но решить получается только через тригер.

причем тригер нужно ставить не на тот объект на котором стоит это "sum-up" поле, а на объект связанных записей, так получается?


но можно ли задачу решить  по другому: а зачем это поле вообще нужно?

дело в том что на головной записи хранится цена (100) общая (суммарная) для всех связанных записей. А на каждой связанной записи есть формульное поле ("Усредненная цена на единицу"), которое должно вытянуть из головной записи эту цену и поделить на кол-во всех записей привязнных в головной записи. Для этого и создаем поле с кол-вом связанных записей на головной записи. Но может кол-во связанных записей можно как-то посчитать в формуле на самой связанной записи. не думаю.

спасибо


Den Brown
Всем привет!

еще одно простая, но насущная задачка.

На записи должно быть поле хранящее кол-во связанных через лук-ап, но не дочерних записей.

вроде задача выглядит просто, но решить получается только через тригер.

причем тригер нужно ставить не на тот объект на котором стоит это "sum-up" поле, а на объект связанных записей, так получается?


но можно ли задачу решить по другому: а зачем это поле вообще нужно?

дело в том что на головной записи хранится цена (100) общая (суммарная) для всех связанных записей. А на каждой связанной записи есть формульное поле ("Усредненная цена на единицу"), которое должно вытянуть из головной записи эту цену и поделить на кол-во всех записей привязнных в головной записи. Для этого и создаем поле с кол-вом связанных записей на головной записи. Но может кол-во связанных записей можно как-то посчитать в формуле на самой связанной записи. не думаю.

спасибо

Такую задачу можно попробовать решить с помощью мастер-детейла, но указать что можно делать reparent для потомка. Решается через роллап саммари и через формула филд.

Если нельзя использовать мастер-дитейл, то только триггер.

[quote="Den Brown"]Всем привет!

еще одно простая, но насущная задачка.

На записи должно быть поле хранящее  кол-во связанных через лук-ап, но не дочерних записей.

вроде задача выглядит просто, но решить получается только через тригер.

причем тригер нужно ставить не на тот объект на котором стоит это "sum-up" поле, а на объект связанных записей, так получается?


но можно ли задачу решить  по другому: а зачем это поле вообще нужно?

дело в том что на головной записи хранится цена (100) общая (суммарная) для всех связанных записей. А на каждой связанной записи есть формульное поле ("Усредненная цена на единицу"), которое должно вытянуть из головной записи эту цену и поделить на кол-во всех записей привязнных в головной записи. Для этого и создаем поле с кол-вом связанных записей на головной записи. Но может кол-во связанных записей можно как-то посчитать в формуле на самой связанной записи. не думаю.

спасибо[/quote]

Такую задачу можно попробовать решить с помощью мастер-детейла, но указать что можно делать reparent для потомка. Решается через роллап саммари и через формула филд. 

Если нельзя использовать мастер-дитейл, то только триггер.

Den Brown
попробовать решить с помощью мастер-детейла, но указать что можно делать reparent

спасибо wilder за быстрый ответ.
эти связанные записи уже дочерние записи др объекта, не хочу никак мутить здесь воду через мастер-детейл только из-зи этого поля, и так все сложно.


придется пилить тригер. А этот связанный объект очень бизи - там кодом создаются записи пачками по тысячи. так что придется писать тригер очень аккуртно...

[quote="Den Brown"]попробовать решить с помощью мастер-детейла, но указать что можно делать reparent [/quote]

спасибо wilder за быстрый ответ. 
эти связанные записи уже дочерние записи др объекта, не хочу никак мутить здесь воду через мастер-детейл только из-зи этого поля, и так все сложно.


придется пилить тригер. А этот связанный объект очень бизи - там кодом создаются записи пачками по тысячи. так что придется писать тригер очень аккуртно...

Вот предложили посмотреть вариант - но это кажется интересным, но сложным:

http://salesforce.stackexchange.com/questions/18097/count-total-child-records-on-parent-object-in-lookup-relationship

Вот предложили посмотреть вариант - но это кажется интересным, но сложным:

http://salesforce.stackexchange.com/questions/18097/count-total-child-records-on-parent-object-in-lookup-relationship

Den Brown
Вот предложили посмотреть вариант - но это кажется интересным, но сложным:

http://salesforce.stackexchange.com/questions/18097/count-total-child-records-on-parent-object-in-lookup-relationship

Ничего там сложного нет. Есть специальный класс который делает делает нужные манипуляции с дочерними объектами.

[quote="Den Brown"]Вот предложили посмотреть вариант - но это кажется интересным, но сложным:

http://salesforce.stackexchange.com/questions/18097/count-total-child-records-on-parent-object-in-lookup-relationship[/quote]

Ничего там сложного нет. Есть специальный класс который делает делает нужные манипуляции с дочерними объектами.

Я попробовал продумать логику тригера, и не могу решить серьезную проблему: не могу избежать установки Селекта в цикл...

Тригер должен стоять на объекте привязанных записей на апдейт, делит и анделит.

но все дело в том что, как изместно, в тригер записи могут прийти пачками, и у каждой записи нужно по признаку Головной записи пересчитать Cоunt()-ом сестринские записи и записать в поле Головной записи значение.

и я не могу как-то обобщить, вывести вне цикла Cоunt() операцию... считать приходится для каждой записи...

плюс еще Cоunt() считает только до 50000...

просто не могу поверить, что такая типичная задача - хранить значение связанных записей оборачивается такими проблемами!

PS: А нет, вроде нашел вариант с волшебным циклом (пример):

for (AggregateResult ar : [
Select Count(Id) numRecs, Account__c acctId
From NPS__c
Where Account__c In :Trigger.New
Group By Account__c
])

и здесь как я понимаю Count() "вставлен" в цикл - но при этом будет считаться единой (одной) операцией?

http://salesforce.stackexchange.com/questions/25489/how-do-i-count-records-on-a-child-custom-object-from-the-parent

ОГО! найденный пример оказался даже более интересным чем кажется, посмотрите на AggregateResult:
http://www.salesforce.com/us/developer/docs/api/Content/sforce_api_calls_query_aggregateresult.htm

но проблема с 50000 наврное все равно остается... (еще нужно проверить платформенные лимиты - это возможно ли что по лук-ап связи висит более 50к записей, по мастер-дитейл вроде как был лимит об этом)

в том же примере вот эта логика кажется мне тоже хорошей:

for(Account a :[SELECT Id,(select id from NPS__r) FROM Account WHERE Id IN: trigger.new])
{
account_map.put(a.id,a.NPS__r.size());
}

только не пойму почему они ставят этот тригер на Головной объект, а не на "дочерний"?! возможно таковы были условия вопроса...

в том же примере вот эта логика кажется мне тоже хорошей:

for(Account a :[SELECT Id,(select id from NPS__r) FROM Account WHERE Id IN: trigger.new])
{
account_map.put(a.id,a.NPS__r.size());
}

только не пойму почему они ставят этот тригер на Головной объект, а не на "дочерний"?! возможно таковы были условия вопроса...

Я попробовал продумать логику тригера, и не могу решить серьезную проблему: не могу избежать установки Селекта в цикл...

Тригер должен стоять на объекте привязанных записей на апдейт, делит и анделит.

но все дело в том что, как изместно, в тригер записи могут прийти пачками, и у каждой записи нужно по признаку Головной записи пересчитать Cоunt()-ом сестринские записи и записать в поле Головной записи значение.

и я не могу как-то обобщить, вывести вне цикла Cоunt() операцию... считать приходится для каждой записи...

плюс еще Cоunt() считает только до 50000...

просто не могу поверить, что такая типичная задача - хранить значение связанных записей оборачивается такими проблемами!

PS: А нет, вроде нашел вариант с волшебным циклом (пример):

for (AggregateResult ar : [
     Select Count(Id) numRecs, Account__c acctId
     From NPS__c
     Where Account__c In :Trigger.New
     Group By Account__c
])

и здесь как я понимаю Count() "вставлен" в цикл - но при этом будет считаться единой (одной) операцией?

http://salesforce.stackexchange.com/questions/25489/how-do-i-count-records-on-a-child-custom-object-from-the-parent

ОГО! найденный пример оказался даже более интересным чем кажется, посмотрите на AggregateResult:
http://www.salesforce.com/us/developer/docs/api/Content/sforce_api_calls_query_aggregateresult.htm

но проблема с 50000 наврное все равно остается... (еще нужно проверить платформенные лимиты - это возможно ли что по лук-ап связи висит более 50к записей, по мастер-дитейл вроде как был лимит об этом)

в том же примере вот эта логика кажется мне тоже хорошей:

    for(Account a :[SELECT Id,([b]select id from NPS__r[/b]) FROM Account WHERE Id IN: trigger.new])
         {
          account_map.put(a.id,[b]a.NPS__r.size()[/b]);       
         }

только не пойму почему они ставят этот тригер на Головной объект, а не на "дочерний"?! возможно таковы были условия вопроса...

в том же примере вот эта логика кажется мне тоже хорошей:

    for(Account a :[SELECT Id,([b]select id from NPS__r[/b]) FROM Account WHERE Id IN: trigger.new])
         {
          account_map.put(a.id,[b]a.NPS__r.size()[/b]);       
         }

только не пойму почему они ставят этот тригер на Головной объект, а не на "дочерний"?! возможно таковы были условия вопроса...

И все-таки подскажите какой вариант более устойчив к Лимитам:


через Count():

for (AggregateResult ar : [
Select Count(Id) numRecs, Account__c acctId
From NPS__c
Where Account__c In :Trigger.New
Group By Account__c
]) {
Id acctId = (Id) ar.get('acctId');
Account acct = Trigger.newMap.get(acctId);
acct.NPS_Score_Trigger__c = (Decimal) ar.get('numRecs');
}

или через .size():

List<Account> accUpdateList = new List<Account>();
For(Account acc : [SELECT Contact_Recs__c,(SELECT id FROM Contacts) FROM Account WHERE id =: accIdList]){
acc.Contact_Recs__c = acc.Contacts.size();
accUpdateList.add(acc);
}

предполагается что связанных записей (подлежащий счету) будут многие тысячи. Хотя в с другой стороны тригер будет фильтровать пришедшие записи и работать только с теми у которых было изменение по связи.

И все-таки подскажите какой вариант более устойчив к Лимитам:


через Count():

for (AggregateResult ar : [
     Select [b]Count(Id[/b]) numRecs, Account__c acctId
     From NPS__c
     Where Account__c In :Trigger.New
     Group By Account__c
]) {
    Id acctId = (Id) ar.get('acctId');
    Account acct = Trigger.newMap.get(acctId);
    acct.NPS_Score_Trigger__c = (Decimal) ar.get('numRecs');
}

или через .size():

    List<Account> accUpdateList = new List<Account>();
    For(Account acc : [SELECT Contact_Recs__c,(SELECT id FROM Contacts) FROM Account WHERE id =: accIdList]){
        acc.Contact_Recs__c = acc.[b]Contacts.size()[/b];
        accUpdateList.add(acc);
    }

предполагается что связанных записей (подлежащий счету) будут многие тысячи. Хотя в с другой стороны тригер будет фильтровать пришедшие записи и работать только с теми у которых было изменение по связи.