mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-03-22 15:19:59 +07:00
IDEA-310984 Usage view statistics collector: added popup.closed event
Added getEventData() ShowUsagesActionHandler for statistcs reporting purposes `popup.closed` logs: * UsageView * if item choseor not * target element language * selected element class * duration of being shown * added target element for the statistics GitOrigin-RevId: c20865b9190c82809181bd0a4cb298c765b3acc3
This commit is contained in:
committed by
intellij-monorepo-bot
parent
27fba5b6c8
commit
b1a6bdab2f
@@ -7,6 +7,7 @@ import com.intellij.find.usages.api.UsageOptions.createOptions
|
||||
import com.intellij.find.usages.impl.AllSearchOptions
|
||||
import com.intellij.find.usages.impl.buildUsageViewQuery
|
||||
import com.intellij.ide.nls.NlsMessages
|
||||
import com.intellij.internal.statistic.eventLog.events.EventPair
|
||||
import com.intellij.lang.LangBundle
|
||||
import com.intellij.lang.Language
|
||||
import com.intellij.openapi.project.Project
|
||||
@@ -68,6 +69,9 @@ internal data class ShowTargetUsagesActionHandler(
|
||||
override fun getTargetLanguage(): Language? = null
|
||||
|
||||
override fun getTargetClass(): Class<*> = target::class.java
|
||||
override fun getEventData(): List<EventPair<*>> {
|
||||
return emptyList();
|
||||
}
|
||||
|
||||
companion object {
|
||||
|
||||
|
||||
@@ -16,6 +16,8 @@ import com.intellij.ide.DataManager;
|
||||
import com.intellij.ide.util.PropertiesComponent;
|
||||
import com.intellij.ide.util.gotoByName.ModelDiff;
|
||||
import com.intellij.ide.util.scopeChooser.ScopeChooserGroup;
|
||||
import com.intellij.internal.statistic.eventLog.events.EventFields;
|
||||
import com.intellij.internal.statistic.eventLog.events.EventPair;
|
||||
import com.intellij.internal.statistic.service.fus.collectors.UIEventLogger;
|
||||
import com.intellij.lang.Language;
|
||||
import com.intellij.lang.injection.InjectedLanguageManager;
|
||||
@@ -44,9 +46,7 @@ import com.intellij.openapi.ui.DialogPanel;
|
||||
import com.intellij.openapi.ui.MessageType;
|
||||
import com.intellij.openapi.ui.OnePixelDivider;
|
||||
import com.intellij.openapi.ui.Splitter;
|
||||
import com.intellij.openapi.ui.popup.JBPopup;
|
||||
import com.intellij.openapi.ui.popup.JBPopupFactory;
|
||||
import com.intellij.openapi.ui.popup.PopupChooserBuilder;
|
||||
import com.intellij.openapi.ui.popup.*;
|
||||
import com.intellij.openapi.ui.popup.util.PopupUtil;
|
||||
import com.intellij.openapi.util.*;
|
||||
import com.intellij.openapi.util.registry.Registry;
|
||||
@@ -373,6 +373,12 @@ public class ShowUsagesAction extends AnAction implements PopupAction, HintManag
|
||||
public @NotNull Class<?> getTargetClass() {
|
||||
return handler.getPsiElement().getClass();
|
||||
}
|
||||
|
||||
@Override
|
||||
public @NotNull List<EventPair<?>> getEventData() {
|
||||
return List.of(UsageViewStatisticsCollector.PRIMARY_TARGET.with(handler.getPsiElement().getClass()),
|
||||
EventFields.Language.with(handler.getPsiElement().getLanguage()));
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@@ -414,7 +420,17 @@ public class ShowUsagesAction extends AnAction implements PopupAction, HintManag
|
||||
AbstractPopup popup = createUsagePopup(usageView, showUsagesPopupData, itemChosenCallback, tableResizer);
|
||||
|
||||
popup.addResizeListener(() -> manuallyResized.set(true), popup);
|
||||
|
||||
Ref<Long> popupShownTime = new Ref<>();
|
||||
popup.addListener(new JBPopupListener() {
|
||||
@Override
|
||||
public void onClosed(@NotNull LightweightWindowEvent event) {
|
||||
Object usageNode = table.getModel().getValueAt(table.getSelectedRow(), 0);
|
||||
UsageInfo2UsageAdapter usageAdapter = getSelectedUsageAdapter(ObjectUtils.tryCast(usageNode, UsageNode.class));
|
||||
UsageViewStatisticsCollector.logPopupClosed(project, usageView, event.isOk(),
|
||||
usageAdapter,
|
||||
popupShownTime.get(), actionHandler.getEventData());
|
||||
}
|
||||
});
|
||||
ProgressIndicator indicator = new ProgressIndicatorBase();
|
||||
if (!popup.isDisposed()) {
|
||||
Disposer.register(popup, usageView);
|
||||
@@ -423,7 +439,7 @@ public class ShowUsagesAction extends AnAction implements PopupAction, HintManag
|
||||
// show popup only if find usages takes more than 300ms, otherwise it would flicker needlessly
|
||||
EdtScheduledExecutorService.getInstance().schedule(() -> {
|
||||
if (!usageView.isDisposed()) {
|
||||
showPopupIfNeedTo(popup, parameters.popupPosition);
|
||||
showPopupIfNeedTo(popup, parameters.popupPosition, popupShownTime);
|
||||
}
|
||||
}, ourPopupDelayTimeout, TimeUnit.MILLISECONDS);
|
||||
}
|
||||
@@ -438,7 +454,7 @@ public class ShowUsagesAction extends AnAction implements PopupAction, HintManag
|
||||
List<Usage> copy;
|
||||
synchronized (usages) {
|
||||
// open up popup as soon as the first usage has been found
|
||||
if (!popup.isVisible() && (usages.isEmpty() || !showPopupIfNeedTo(popup, parameters.popupPosition))) {
|
||||
if (!popup.isVisible() && (usages.isEmpty() || !showPopupIfNeedTo(popup, parameters.popupPosition, popupShownTime))) {
|
||||
return;
|
||||
}
|
||||
addUsageNodes(usageView.getRoot(), usageView, nodes);
|
||||
@@ -618,9 +634,10 @@ public class ShowUsagesAction extends AnAction implements PopupAction, HintManag
|
||||
return __ -> false;
|
||||
}
|
||||
|
||||
private static boolean showPopupIfNeedTo(@NotNull JBPopup popup, @NotNull RelativePoint popupPosition) {
|
||||
private static boolean showPopupIfNeedTo(@NotNull JBPopup popup, @NotNull RelativePoint popupPosition, Ref<Long> popupShownTime) {
|
||||
if (!popup.isDisposed() && !popup.isVisible()) {
|
||||
popup.show(popupPosition);
|
||||
popupShownTime.set(System.currentTimeMillis());
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
@@ -1032,6 +1049,14 @@ public class ShowUsagesAction extends AnAction implements PopupAction, HintManag
|
||||
return (int)usages.stream().filter(usage -> !usageView.isVisible(usage)).count();
|
||||
}
|
||||
|
||||
private static @Nullable UsageInfo2UsageAdapter getSelectedUsageAdapter(@Nullable UsageNode usageNode) {
|
||||
UsageInfo2UsageAdapter usageAdapter = null;
|
||||
if (usageNode != null) {
|
||||
usageAdapter = ObjectUtils.tryCast(usageNode.getUsage(), UsageInfo2UsageAdapter.class);
|
||||
}
|
||||
return usageAdapter;
|
||||
}
|
||||
|
||||
private static int getUsageOffset(@NotNull Usage usage) {
|
||||
if (!(usage instanceof UsageInfo2UsageAdapter)) return -1;
|
||||
PsiElement element = ((UsageInfo2UsageAdapter)usage).getElement();
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
package com.intellij.find.actions;
|
||||
|
||||
import com.intellij.find.FindBundle;
|
||||
import com.intellij.internal.statistic.eventLog.events.EventPair;
|
||||
import com.intellij.lang.Language;
|
||||
import com.intellij.openapi.actionSystem.KeyboardShortcut;
|
||||
import com.intellij.openapi.keymap.KeymapUtil;
|
||||
@@ -13,6 +14,8 @@ import com.intellij.usages.UsageSearcher;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
interface ShowUsagesActionHandler {
|
||||
|
||||
boolean isValid();
|
||||
@@ -35,6 +38,8 @@ interface ShowUsagesActionHandler {
|
||||
|
||||
@NotNull Class<?> getTargetClass();
|
||||
|
||||
@NotNull List<EventPair<?>> getEventData();
|
||||
|
||||
static @PopupAdvertisement @Nullable String getSecondInvocationHint(@NotNull ShowUsagesActionHandler actionHandler) {
|
||||
KeyboardShortcut shortcut = ShowUsagesAction.getShowUsagesShortcut();
|
||||
if (shortcut == null) {
|
||||
|
||||
@@ -5,6 +5,7 @@ import com.intellij.ide.util.scopeChooser.ScopeIdMapper
|
||||
import com.intellij.internal.statistic.eventLog.EventLogGroup
|
||||
import com.intellij.internal.statistic.eventLog.FeatureUsageData
|
||||
import com.intellij.internal.statistic.eventLog.events.EventFields
|
||||
import com.intellij.internal.statistic.eventLog.events.EventPair
|
||||
import com.intellij.internal.statistic.eventLog.events.PrimitiveEventField
|
||||
import com.intellij.internal.statistic.eventLog.validator.ValidationResultType
|
||||
import com.intellij.internal.statistic.eventLog.validator.rules.EventContext
|
||||
@@ -16,8 +17,10 @@ import com.intellij.psi.PsiElement
|
||||
import com.intellij.psi.search.SearchScope
|
||||
import com.intellij.usageView.UsageInfo
|
||||
import com.intellij.usages.Usage
|
||||
import com.intellij.usages.UsageInfo2UsageAdapter
|
||||
import com.intellij.usages.UsageView
|
||||
import com.intellij.usages.rules.PsiElementUsage
|
||||
import com.intellij.util.containers.ContainerUtil
|
||||
import org.jetbrains.annotations.Nls
|
||||
|
||||
enum class CodeNavigateSource {
|
||||
@@ -35,7 +38,7 @@ class UsageViewStatisticsCollector : CounterUsagesCollector() {
|
||||
override fun getGroup() = GROUP
|
||||
|
||||
companion object {
|
||||
val GROUP = EventLogGroup("usage.view", 16)
|
||||
val GROUP = EventLogGroup("usage.view", 17)
|
||||
val USAGE_VIEW = object : PrimitiveEventField<UsageView?>() {
|
||||
override val name: String = "usage_view"
|
||||
|
||||
@@ -46,7 +49,9 @@ class UsageViewStatisticsCollector : CounterUsagesCollector() {
|
||||
override val validationRule: List<String>
|
||||
get() = listOf("{regexp#integer}")
|
||||
}
|
||||
private val PRIMARY_TARGET = EventFields.Class("primary_target")
|
||||
|
||||
@JvmField
|
||||
val PRIMARY_TARGET = EventFields.Class("primary_target")
|
||||
private val REFERENCE_CLASS = EventFields.Class("reference_class")
|
||||
private val UI_LOCATION = EventFields.Enum("ui_location", CodeNavigateSource::class.java)
|
||||
private val USAGE_SHOWN = GROUP.registerVarargEvent("usage.shown", USAGE_VIEW, REFERENCE_CLASS, EventFields.Language, UI_LOCATION)
|
||||
@@ -102,6 +107,10 @@ class UsageViewStatisticsCollector : CounterUsagesCollector() {
|
||||
private val scopeChanged = GROUP.registerVarargEvent("scope.changed", USAGE_VIEW, PREVIOUS_SCOPE, NEW_SCOPE, SYMBOL_CLASS)
|
||||
private val OPEN_IN_FIND_TOOL_WINDOW = GROUP.registerEvent("open.in.tool.window", USAGE_VIEW)
|
||||
private val USER_ACTION = EventFields.Enum("userAction", TooManyUsagesUserAction::class.java)
|
||||
private val ITEM_CHOSEN = EventFields.Boolean("item_chosen")
|
||||
private val popupClosed = GROUP.registerVarargEvent(
|
||||
"popup.closed", USAGE_VIEW, ITEM_CHOSEN, PRIMARY_TARGET, EventFields.Language, REFERENCE_CLASS, EventFields.DurationMs
|
||||
)
|
||||
private val tooManyUsagesDialog = GROUP.registerVarargEvent("tooManyResultsDialog",
|
||||
USAGE_VIEW,
|
||||
USER_ACTION,
|
||||
@@ -264,6 +273,23 @@ class UsageViewStatisticsCollector : CounterUsagesCollector() {
|
||||
fun logOpenInFindToolWindow(project: Project?, usageView: UsageView) =
|
||||
OPEN_IN_FIND_TOOL_WINDOW.log(project, usageView)
|
||||
|
||||
@JvmStatic
|
||||
fun logPopupClosed(project: Project?,
|
||||
usageView: UsageView,
|
||||
itemChosen: Boolean,
|
||||
usage: UsageInfo2UsageAdapter?,
|
||||
startTime: Long?,
|
||||
showUsagesHandlerEventData: List<EventPair<*>>) {
|
||||
val data = mutableListOf(USAGE_VIEW.with(usageView), ITEM_CHOSEN.with(itemChosen),
|
||||
REFERENCE_CLASS.with(
|
||||
usage?.referenceClass
|
||||
))
|
||||
data.addAll(showUsagesHandlerEventData)
|
||||
if (startTime != null) {
|
||||
data.add(EventFields.DurationMs.with(System.currentTimeMillis() - startTime))
|
||||
}
|
||||
popupClosed.log(project, data)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user