feat: Enable bulk analytics vocab deletion (#5677)

This commit is contained in:
ggurdin 2026-02-12 12:22:55 -05:00 committed by GitHub
parent 451705929f
commit c91cb1ca77
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
9 changed files with 221 additions and 153 deletions

View file

@ -8,11 +8,8 @@
/* Begin PBXBuildFile section */
1498D2341E8E89220040F4C2 /* GeneratedPluginRegistrant.m in Sources */ = {isa = PBXBuildFile; fileRef = 1498D2331E8E89220040F4C2 /* GeneratedPluginRegistrant.m */; };
18EB8101724ECEB31DC90D37 /* (null) in Frameworks */ = {isa = PBXBuildFile; };
18EB8101724ECEB31DC90D37 /* BuildFile in Frameworks */ = {isa = PBXBuildFile; };
3B3967161E833CAA004F5970 /* AppFrameworkInfo.plist in Resources */ = {isa = PBXBuildFile; fileRef = 3B3967151E833CAA004F5970 /* AppFrameworkInfo.plist */; };
3F86C7E35D199E7DD2B134F9 /* Pods_Runner.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 69EC0FDC95BB0C70B544A84C /* Pods_Runner.framework */; };
59BB4671C68B58E6B34292B2 /* Pods_FluffyChat_Share.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 52740D3A973E95DFFBA1E6CD /* Pods_FluffyChat_Share.framework */; };
609046320A2D7D2B0D36583B /* Pods_FluffyChat_Share.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = C9EB6E6475A19949A37A2634 /* Pods_FluffyChat_Share.framework */; };
74858FAF1ED2DC5600515810 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 74858FAE1ED2DC5600515810 /* AppDelegate.swift */; };
97C146FC1CF9000F007C117D /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 97C146FA1CF9000F007C117D /* Main.storyboard */; };
97C146FE1CF9000F007C117D /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 97C146FD1CF9000F007C117D /* Assets.xcassets */; };
@ -26,6 +23,8 @@
C14695672E642E450075F2F7 /* Localizable.xcstrings in Resources */ = {isa = PBXBuildFile; fileRef = C14695652E642E450075F2F7 /* Localizable.xcstrings */; };
C14695682E642E450075F2F7 /* Localizable.xcstrings in Resources */ = {isa = PBXBuildFile; fileRef = C14695652E642E450075F2F7 /* Localizable.xcstrings */; };
C149567C25C7274F00A16396 /* GoogleService-Info.plist in Resources */ = {isa = PBXBuildFile; fileRef = C149567B25C7274F00A16396 /* GoogleService-Info.plist */; };
D90BF3860281059CF0968424 /* Pods_Runner.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = F271E2B813870B06CCCADE7C /* Pods_Runner.framework */; };
EBB7056EEC2CACBC25CF7B8D /* Pods_FluffyChat_Share.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 990FF3710347D35B1879605B /* Pods_FluffyChat_Share.framework */; };
/* End PBXBuildFile section */
/* Begin PBXContainerItemProxy section */
@ -71,15 +70,11 @@
/* End PBXCopyFilesBuildPhase section */
/* Begin PBXFileReference section */
09545B0C8C397F94966EA956 /* Pods-FluffyChat Share.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-FluffyChat Share.debug.xcconfig"; path = "Target Support Files/Pods-FluffyChat Share/Pods-FluffyChat Share.debug.xcconfig"; sourceTree = "<group>"; };
1498D2321E8E86230040F4C2 /* GeneratedPluginRegistrant.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = GeneratedPluginRegistrant.h; sourceTree = "<group>"; };
1498D2331E8E89220040F4C2 /* GeneratedPluginRegistrant.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GeneratedPluginRegistrant.m; sourceTree = "<group>"; };
23120B990D2B5081843FB313 /* Pods-Runner.profile.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.profile.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.profile.xcconfig"; sourceTree = "<group>"; };
37AEBFB57FB2CB2626CFE6E0 /* Pods-Runner.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.debug.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.debug.xcconfig"; sourceTree = "<group>"; };
351C73FC7DC0AED8C01170AA /* Pods-FluffyChat Share.profile.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-FluffyChat Share.profile.xcconfig"; path = "Target Support Files/Pods-FluffyChat Share/Pods-FluffyChat Share.profile.xcconfig"; sourceTree = "<group>"; };
3B3967151E833CAA004F5970 /* AppFrameworkInfo.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; name = AppFrameworkInfo.plist; path = Flutter/AppFrameworkInfo.plist; sourceTree = "<group>"; };
52740D3A973E95DFFBA1E6CD /* Pods_FluffyChat_Share.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_FluffyChat_Share.framework; sourceTree = BUILT_PRODUCTS_DIR; };
58F7B95D036AD8E67B27588D /* Pods-FluffyChat Share.profile.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-FluffyChat Share.profile.xcconfig"; path = "Target Support Files/Pods-FluffyChat Share/Pods-FluffyChat Share.profile.xcconfig"; sourceTree = "<group>"; };
69EC0FDC95BB0C70B544A84C /* Pods_Runner.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_Runner.framework; sourceTree = BUILT_PRODUCTS_DIR; };
3F5E3824ED785E4EFC2E3DD1 /* Pods-Runner.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.debug.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.debug.xcconfig"; sourceTree = "<group>"; };
74858FAD1ED2DC5600515810 /* Runner-Bridging-Header.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "Runner-Bridging-Header.h"; sourceTree = "<group>"; };
74858FAE1ED2DC5600515810 /* AppDelegate.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = "<group>"; };
7AFA3C8E1D35360C0083082E /* Release.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; name = Release.xcconfig; path = Flutter/Release.xcconfig; sourceTree = "<group>"; };
@ -90,6 +85,10 @@
97C146FD1CF9000F007C117D /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = "<group>"; };
97C147001CF9000F007C117D /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = "<group>"; };
97C147021CF9000F007C117D /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
990FF3710347D35B1879605B /* Pods_FluffyChat_Share.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_FluffyChat_Share.framework; sourceTree = BUILT_PRODUCTS_DIR; };
A307EC9E45C5B6CC17012930 /* Pods-Runner.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.release.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.release.xcconfig"; sourceTree = "<group>"; };
B390DA5EE2AFAD7F6678DF09 /* Pods-Runner.profile.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.profile.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.profile.xcconfig"; sourceTree = "<group>"; };
B3B2B1A52DF9C9C8DE61A5A6 /* Pods-FluffyChat Share.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-FluffyChat Share.debug.xcconfig"; path = "Target Support Files/Pods-FluffyChat Share/Pods-FluffyChat Share.debug.xcconfig"; sourceTree = "<group>"; };
C1005C42261071B5002F4F32 /* FluffyChat Share.appex */ = {isa = PBXFileReference; explicitFileType = "wrapper.app-extension"; includeInIndex = 0; path = "FluffyChat Share.appex"; sourceTree = BUILT_PRODUCTS_DIR; };
C1005C44261071B5002F4F32 /* ShareViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ShareViewController.swift; sourceTree = "<group>"; };
C1005C47261071B5002F4F32 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/MainInterface.storyboard; sourceTree = "<group>"; };
@ -100,9 +99,8 @@
C14695652E642E450075F2F7 /* Localizable.xcstrings */ = {isa = PBXFileReference; lastKnownFileType = text.json.xcstrings; path = Localizable.xcstrings; sourceTree = "<group>"; };
C149567B25C7274F00A16396 /* GoogleService-Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = "GoogleService-Info.plist"; sourceTree = "<group>"; };
C149567D25C7276200A16396 /* Runner.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = Runner.entitlements; sourceTree = "<group>"; };
C9EB6E6475A19949A37A2634 /* Pods_FluffyChat_Share.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_FluffyChat_Share.framework; sourceTree = BUILT_PRODUCTS_DIR; };
EA246783222E02DD03959891 /* Pods-Runner.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.release.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.release.xcconfig"; sourceTree = "<group>"; };
F3778959E67CDA0CDB0D97BC /* Pods-FluffyChat Share.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-FluffyChat Share.release.xcconfig"; path = "Target Support Files/Pods-FluffyChat Share/Pods-FluffyChat Share.release.xcconfig"; sourceTree = "<group>"; };
CBA0FA8580CE2E2BA482335D /* Pods-FluffyChat Share.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-FluffyChat Share.release.xcconfig"; path = "Target Support Files/Pods-FluffyChat Share/Pods-FluffyChat Share.release.xcconfig"; sourceTree = "<group>"; };
F271E2B813870B06CCCADE7C /* Pods_Runner.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_Runner.framework; sourceTree = BUILT_PRODUCTS_DIR; };
/* End PBXFileReference section */
/* Begin PBXFileSystemSynchronizedBuildFileExceptionSet section */
@ -131,8 +129,8 @@
isa = PBXFrameworksBuildPhase;
buildActionMask = 2147483647;
files = (
18EB8101724ECEB31DC90D37 /* (null) in Frameworks */,
3F86C7E35D199E7DD2B134F9 /* Pods_Runner.framework in Frameworks */,
18EB8101724ECEB31DC90D37 /* BuildFile in Frameworks */,
D90BF3860281059CF0968424 /* Pods_Runner.framework in Frameworks */,
);
runOnlyForDeploymentPostprocessing = 0;
};
@ -140,8 +138,7 @@
isa = PBXFrameworksBuildPhase;
buildActionMask = 2147483647;
files = (
609046320A2D7D2B0D36583B /* Pods_FluffyChat_Share.framework in Frameworks */,
59BB4671C68B58E6B34292B2 /* Pods_FluffyChat_Share.framework in Frameworks */,
EBB7056EEC2CACBC25CF7B8D /* Pods_FluffyChat_Share.framework in Frameworks */,
);
runOnlyForDeploymentPostprocessing = 0;
};
@ -155,10 +152,18 @@
/* End PBXFrameworksBuildPhase section */
/* Begin PBXGroup section */
218A008D9DB828C97780D5A8 /* Frameworks */ = {
isa = PBXGroup;
children = (
990FF3710347D35B1879605B /* Pods_FluffyChat_Share.framework */,
F271E2B813870B06CCCADE7C /* Pods_Runner.framework */,
);
name = Frameworks;
sourceTree = "<group>";
};
7D5C7F242D2C878500101753 /* Recovered References */ = {
isa = PBXGroup;
children = (
C9EB6E6475A19949A37A2634 /* Pods_FluffyChat_Share.framework */,
);
name = "Recovered References";
sourceTree = "<group>";
@ -184,8 +189,8 @@
C14695532E642D400075F2F7 /* Notification Service Extension */,
97C146EF1CF9000F007C117D /* Products */,
E89DCAC000D371640E94E65B /* Pods */,
E4B51FC6310E8231ADAAC605 /* Frameworks */,
7D5C7F242D2C878500101753 /* Recovered References */,
218A008D9DB828C97780D5A8 /* Frameworks */,
);
sourceTree = "<group>";
};
@ -228,24 +233,15 @@
path = "FluffyChat Share";
sourceTree = "<group>";
};
E4B51FC6310E8231ADAAC605 /* Frameworks */ = {
isa = PBXGroup;
children = (
52740D3A973E95DFFBA1E6CD /* Pods_FluffyChat_Share.framework */,
69EC0FDC95BB0C70B544A84C /* Pods_Runner.framework */,
);
name = Frameworks;
sourceTree = "<group>";
};
E89DCAC000D371640E94E65B /* Pods */ = {
isa = PBXGroup;
children = (
EA246783222E02DD03959891 /* Pods-Runner.release.xcconfig */,
09545B0C8C397F94966EA956 /* Pods-FluffyChat Share.debug.xcconfig */,
F3778959E67CDA0CDB0D97BC /* Pods-FluffyChat Share.release.xcconfig */,
58F7B95D036AD8E67B27588D /* Pods-FluffyChat Share.profile.xcconfig */,
37AEBFB57FB2CB2626CFE6E0 /* Pods-Runner.debug.xcconfig */,
23120B990D2B5081843FB313 /* Pods-Runner.profile.xcconfig */,
B3B2B1A52DF9C9C8DE61A5A6 /* Pods-FluffyChat Share.debug.xcconfig */,
CBA0FA8580CE2E2BA482335D /* Pods-FluffyChat Share.release.xcconfig */,
351C73FC7DC0AED8C01170AA /* Pods-FluffyChat Share.profile.xcconfig */,
3F5E3824ED785E4EFC2E3DD1 /* Pods-Runner.debug.xcconfig */,
A307EC9E45C5B6CC17012930 /* Pods-Runner.release.xcconfig */,
B390DA5EE2AFAD7F6678DF09 /* Pods-Runner.profile.xcconfig */,
);
path = Pods;
sourceTree = "<group>";
@ -257,7 +253,7 @@
isa = PBXNativeTarget;
buildConfigurationList = 97C147051CF9000F007C117D /* Build configuration list for PBXNativeTarget "Runner" */;
buildPhases = (
57BA887B93F55975BC09DE22 /* [CP] Check Pods Manifest.lock */,
9DF0E54B7790E57647F8FF6C /* [CP] Check Pods Manifest.lock */,
9740EEB61CF901F6004384FC /* Run Script */,
97C146EA1CF9000F007C117D /* Sources */,
97C146EB1CF9000F007C117D /* Frameworks */,
@ -265,8 +261,8 @@
C1005C4D261071B5002F4F32 /* Embed App Extensions */,
9705A1C41CF9048500538489 /* Embed Frameworks */,
3B06AD1E1E4923F5004D2608 /* Thin Binary */,
334226A3AAA43B66497B29BC /* [CP] Embed Pods Frameworks */,
1A28566378F0961D311DA2BA /* [CP] Copy Pods Resources */,
DE9BF9B39C849ABDDE8B2581 /* [CP] Embed Pods Frameworks */,
FE3E139D83F35A3030A93A4F /* [CP] Copy Pods Resources */,
);
buildRules = (
);
@ -283,7 +279,7 @@
isa = PBXNativeTarget;
buildConfigurationList = C1005C51261071B5002F4F32 /* Build configuration list for PBXNativeTarget "FluffyChat Share" */;
buildPhases = (
67579C1EA0B5C7B918473158 /* [CP] Check Pods Manifest.lock */,
61F3F13146B92C7B2A2FFC84 /* [CP] Check Pods Manifest.lock */,
C1005C3E261071B5002F4F32 /* Sources */,
C1005C3F261071B5002F4F32 /* Frameworks */,
C1005C40261071B5002F4F32 /* Resources */,
@ -395,40 +391,6 @@
/* End PBXResourcesBuildPhase section */
/* Begin PBXShellScriptBuildPhase section */
1A28566378F0961D311DA2BA /* [CP] Copy Pods Resources */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputFileListPaths = (
"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources-${CONFIGURATION}-input-files.xcfilelist",
);
name = "[CP] Copy Pods Resources";
outputFileListPaths = (
"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources-${CONFIGURATION}-output-files.xcfilelist",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "\"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources.sh\"\n";
showEnvVarsInLog = 0;
};
334226A3AAA43B66497B29BC /* [CP] Embed Pods Frameworks */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputFileListPaths = (
"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-frameworks-${CONFIGURATION}-input-files.xcfilelist",
);
name = "[CP] Embed Pods Frameworks";
outputFileListPaths = (
"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-frameworks-${CONFIGURATION}-output-files.xcfilelist",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "\"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-frameworks.sh\"\n";
showEnvVarsInLog = 0;
};
3B06AD1E1E4923F5004D2608 /* Thin Binary */ = {
isa = PBXShellScriptBuildPhase;
alwaysOutOfDate = 1;
@ -445,29 +407,7 @@
shellPath = /bin/sh;
shellScript = "/bin/sh \"$FLUTTER_ROOT/packages/flutter_tools/bin/xcode_backend.sh\" embed_and_thin\n";
};
57BA887B93F55975BC09DE22 /* [CP] Check Pods Manifest.lock */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputFileListPaths = (
);
inputPaths = (
"${PODS_PODFILE_DIR_PATH}/Podfile.lock",
"${PODS_ROOT}/Manifest.lock",
);
name = "[CP] Check Pods Manifest.lock";
outputFileListPaths = (
);
outputPaths = (
"$(DERIVED_FILE_DIR)/Pods-Runner-checkManifestLockResult.txt",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "diff \"${PODS_PODFILE_DIR_PATH}/Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [ $? != 0 ] ; then\n # print error to STDERR\n echo \"error: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\" >&2\n exit 1\nfi\n# This output is used by Xcode 'outputs' to avoid re-running this script phase.\necho \"SUCCESS\" > \"${SCRIPT_OUTPUT_FILE_0}\"\n";
showEnvVarsInLog = 0;
};
67579C1EA0B5C7B918473158 /* [CP] Check Pods Manifest.lock */ = {
61F3F13146B92C7B2A2FFC84 /* [CP] Check Pods Manifest.lock */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
@ -504,6 +444,62 @@
shellPath = /bin/sh;
shellScript = "/bin/sh \"$FLUTTER_ROOT/packages/flutter_tools/bin/xcode_backend.sh\" build\n";
};
9DF0E54B7790E57647F8FF6C /* [CP] Check Pods Manifest.lock */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputFileListPaths = (
);
inputPaths = (
"${PODS_PODFILE_DIR_PATH}/Podfile.lock",
"${PODS_ROOT}/Manifest.lock",
);
name = "[CP] Check Pods Manifest.lock";
outputFileListPaths = (
);
outputPaths = (
"$(DERIVED_FILE_DIR)/Pods-Runner-checkManifestLockResult.txt",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "diff \"${PODS_PODFILE_DIR_PATH}/Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [ $? != 0 ] ; then\n # print error to STDERR\n echo \"error: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\" >&2\n exit 1\nfi\n# This output is used by Xcode 'outputs' to avoid re-running this script phase.\necho \"SUCCESS\" > \"${SCRIPT_OUTPUT_FILE_0}\"\n";
showEnvVarsInLog = 0;
};
DE9BF9B39C849ABDDE8B2581 /* [CP] Embed Pods Frameworks */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputFileListPaths = (
"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-frameworks-${CONFIGURATION}-input-files.xcfilelist",
);
name = "[CP] Embed Pods Frameworks";
outputFileListPaths = (
"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-frameworks-${CONFIGURATION}-output-files.xcfilelist",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "\"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-frameworks.sh\"\n";
showEnvVarsInLog = 0;
};
FE3E139D83F35A3030A93A4F /* [CP] Copy Pods Resources */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputFileListPaths = (
"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources-${CONFIGURATION}-input-files.xcfilelist",
);
name = "[CP] Copy Pods Resources";
outputFileListPaths = (
"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources-${CONFIGURATION}-output-files.xcfilelist",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "\"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-resources.sh\"\n";
showEnvVarsInLog = 0;
};
/* End PBXShellScriptBuildPhase section */
/* Begin PBXSourcesBuildPhase section */
@ -849,7 +845,7 @@
};
C1005C4E261071B5002F4F32 /* Debug */ = {
isa = XCBuildConfiguration;
baseConfigurationReference = 09545B0C8C397F94966EA956 /* Pods-FluffyChat Share.debug.xcconfig */;
baseConfigurationReference = B3B2B1A52DF9C9C8DE61A5A6 /* Pods-FluffyChat Share.debug.xcconfig */;
buildSettings = {
CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
@ -885,7 +881,7 @@
};
C1005C4F261071B5002F4F32 /* Release */ = {
isa = XCBuildConfiguration;
baseConfigurationReference = F3778959E67CDA0CDB0D97BC /* Pods-FluffyChat Share.release.xcconfig */;
baseConfigurationReference = CBA0FA8580CE2E2BA482335D /* Pods-FluffyChat Share.release.xcconfig */;
buildSettings = {
CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
@ -911,6 +907,7 @@
PRODUCT_NAME = "$(TARGET_NAME)";
SKIP_INSTALL = YES;
SUPPORTED_PLATFORMS = "iphonesimulator iphoneos";
SWIFT_ENABLE_EXPLICIT_MODULES = NO;
SWIFT_VERSION = 5.0;
TARGETED_DEVICE_FAMILY = "1,2";
};
@ -918,7 +915,7 @@
};
C1005C50261071B5002F4F32 /* Profile */ = {
isa = XCBuildConfiguration;
baseConfigurationReference = 58F7B95D036AD8E67B27588D /* Pods-FluffyChat Share.profile.xcconfig */;
baseConfigurationReference = 351C73FC7DC0AED8C01170AA /* Pods-FluffyChat Share.profile.xcconfig */;
buildSettings = {
CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
@ -944,6 +941,7 @@
PRODUCT_NAME = "$(TARGET_NAME)";
SKIP_INSTALL = YES;
SUPPORTED_PLATFORMS = "iphonesimulator iphoneos";
SWIFT_ENABLE_EXPLICIT_MODULES = NO;
SWIFT_VERSION = 5.0;
TARGETED_DEVICE_FAMILY = "1,2";
};

View file

@ -34,12 +34,12 @@ class _AnalyticsClient {
class AnalyticsStreamUpdate {
final int points;
final ConstructIdentifier? blockedConstruct;
final Set<ConstructIdentifier>? blockedConstructs;
final String? targetID;
AnalyticsStreamUpdate({
this.points = 0,
this.blockedConstruct,
this.blockedConstructs,
this.targetID,
});
}

View file

@ -152,11 +152,10 @@ class AnalyticsSyncController {
final prevBlocked = prev?.blockedConstructs ?? {};
final newlyBlocked = newBlocked.where((c) => !prevBlocked.contains(c));
for (final constructId in newlyBlocked) {
await dataService.updateDispatcher.sendBlockedConstructUpdate(
constructId,
);
}
if (newlyBlocked.isEmpty) continue;
await dataService.updateDispatcher.sendBlockedConstructsUpdate(
newlyBlocked.toSet(),
);
}
}

View file

@ -85,11 +85,13 @@ class AnalyticsUpdateDispatcher {
UserSetLemmaInfo lemmaInfo,
) => _lemmaInfoUpdateStream.add(MapEntry(constructId, lemmaInfo));
Future<void> sendBlockedConstructUpdate(
ConstructIdentifier blockedConstruct,
Future<void> sendBlockedConstructsUpdate(
Set<ConstructIdentifier> blockedConstructs,
) async {
await dataService.updateBlockedConstructs(blockedConstruct);
final update = AnalyticsStreamUpdate(blockedConstruct: blockedConstruct);
for (final blockedConstruct in blockedConstructs) {
await dataService.updateBlockedConstructs(blockedConstruct);
}
final update = AnalyticsStreamUpdate(blockedConstructs: blockedConstructs);
constructUpdateStream.add(update);
}

View file

@ -129,14 +129,14 @@ class AnalyticsUpdateService {
await analyticsRoom.addActivityRoomId(roomId);
}
Future<void> blockConstruct(ConstructIdentifier constructId) async {
Future<void> blockConstructs(List<ConstructIdentifier> constructIds) async {
final analyticsRoom = await _getAnalyticsRoom();
if (analyticsRoom == null) return;
final current = analyticsRoom.analyticsSettings;
final blockedConstructs = current.blockedConstructs;
final updated = current.copyWith(
blockedConstructs: {...blockedConstructs, constructId},
blockedConstructs: {...blockedConstructs, ...constructIds},
);
await analyticsRoom.setAnalyticsSettings(updated);

View file

@ -2,6 +2,7 @@ import 'dart:async';
import 'package:flutter/material.dart';
import 'package:async/async.dart';
import 'package:diacritic/diacritic.dart';
import 'package:go_router/go_router.dart';
import 'package:material_symbols_icons/symbols.dart';
@ -26,6 +27,8 @@ import 'package:fluffychat/pangea/morphs/morph_repo.dart';
import 'package:fluffychat/pangea/phonetic_transcription/pt_v2_models.dart';
import 'package:fluffychat/pangea/token_info_feedback/show_token_feedback_dialog.dart';
import 'package:fluffychat/pangea/token_info_feedback/token_info_feedback_request.dart';
import 'package:fluffychat/widgets/adaptive_dialogs/show_ok_cancel_alert_dialog.dart';
import 'package:fluffychat/widgets/future_loading_dialog.dart';
import 'package:fluffychat/widgets/matrix.dart';
class ConstructAnalyticsView extends StatefulWidget {
@ -40,6 +43,7 @@ class ConstructAnalyticsView extends StatefulWidget {
class ConstructAnalyticsViewState extends State<ConstructAnalyticsView> {
final TextEditingController searchController = TextEditingController();
final List<ConstructIdentifier> selectedConstructs = [];
MorphFeaturesAndTags morphs = defaultMorphMapping;
List<MorphFeature> features = defaultMorphMapping.displayFeatures;
@ -84,7 +88,7 @@ class ConstructAnalyticsViewState extends State<ConstructAnalyticsView> {
}
void _onConstructUpdate(AnalyticsStreamUpdate update) {
if (update.blockedConstruct != null) {
if (update.blockedConstructs != null) {
_onBlockConstruct(update);
} else {
_setAnalyticsData();
@ -92,9 +96,9 @@ class ConstructAnalyticsViewState extends State<ConstructAnalyticsView> {
}
void _onBlockConstruct(AnalyticsStreamUpdate update) {
final blocked = update.blockedConstruct;
final blocked = update.blockedConstructs;
if (blocked == null) return;
vocab?.removeWhere((e) => e.id == blocked);
vocab?.removeWhere((e) => blocked.contains(e.id));
if (widget.view == ConstructTypeEnum.vocab && widget.construct == null) {
setState(() {});
}
@ -139,6 +143,31 @@ class ConstructAnalyticsViewState extends State<ConstructAnalyticsView> {
}
}
Future<Result<void>?> blockConstructs(
List<ConstructIdentifier> constructs,
) async {
final resp = await showOkCancelAlertDialog(
context: context,
title: L10n.of(context).areYouSure,
message: L10n.of(context).blockLemmaConfirmation,
isDestructive: true,
);
if (resp != OkCancelResult.ok) return null;
return showFutureLoadingDialog(
context: context,
future: () => Matrix.of(
context,
).analyticsDataService.updateService.blockConstructs(constructs),
);
}
Future<void> blockSelectedConstructs() async {
final res = await blockConstructs(selectedConstructs);
if (res == null || res.isError) return;
clearSelectedConstructs();
}
void setSelectedConstructLevel(ConstructLevelEnum level) {
setState(() {
selectedConstructLevel = selectedConstructLevel == level ? null : level;
@ -161,6 +190,24 @@ class ConstructAnalyticsViewState extends State<ConstructAnalyticsView> {
});
}
void toggleSelectedConstruct(ConstructIdentifier construct) {
setState(() {
if (selectedConstructs.contains(construct)) {
selectedConstructs.remove(construct);
} else {
selectedConstructs.add(construct);
}
});
}
void clearSelectedConstructs() {
setState(() {
selectedConstructs.clear();
});
}
bool get selectMode => selectedConstructs.isNotEmpty;
Future<void> onFlagTokenInfo(
PangeaToken token,
LemmaInfoResponse lemmaInfo,

View file

@ -15,8 +15,6 @@ import 'package:fluffychat/pangea/lemmas/lemma.dart';
import 'package:fluffychat/pangea/lemmas/lemma_info_response.dart';
import 'package:fluffychat/pangea/phonetic_transcription/pt_v2_models.dart';
import 'package:fluffychat/pangea/toolbar/word_card/word_zoom_widget.dart';
import 'package:fluffychat/widgets/adaptive_dialogs/show_ok_cancel_alert_dialog.dart';
import 'package:fluffychat/widgets/future_loading_dialog.dart';
import 'package:fluffychat/widgets/layouts/max_width_body.dart';
import 'package:fluffychat/widgets/matrix.dart';
@ -31,27 +29,6 @@ class VocabDetailsView extends StatelessWidget {
required this.controller,
});
Future<void> _blockLemma(BuildContext context) async {
final resp = await showOkCancelAlertDialog(
context: context,
title: L10n.of(context).areYouSure,
message: L10n.of(context).blockLemmaConfirmation,
isDestructive: true,
);
if (resp != OkCancelResult.ok) return;
final res = await showFutureLoadingDialog(
context: context,
future: () => Matrix.of(
context,
).analyticsDataService.updateService.blockConstruct(constructId),
);
if (!res.isError) {
Navigator.of(context).pop();
}
}
@override
Widget build(BuildContext context) {
final analyticsService = Matrix.of(context).analyticsDataService;
@ -143,7 +120,13 @@ class VocabDetailsView extends StatelessWidget {
color: Theme.of(context).colorScheme.error,
),
),
onTap: () => _blockLemma(context),
onTap: () async {
final res = await controller.blockConstructs([
constructId,
]);
if (res == null || res.isError) return;
Navigator.of(context).pop();
},
),
],
),

View file

@ -9,6 +9,7 @@ import 'package:fluffychat/widgets/matrix.dart';
class VocabAnalyticsListTile extends StatelessWidget {
final void Function()? onTap;
final void Function()? onLongPress;
final ConstructIdentifier constructId;
final ConstructLevelEnum level;
final Color textColor;
@ -20,6 +21,7 @@ class VocabAnalyticsListTile extends StatelessWidget {
this.level = ConstructLevelEnum.seeds,
required this.textColor,
this.onTap,
this.onLongPress,
this.selected = false,
});
@ -35,6 +37,7 @@ class VocabAnalyticsListTile extends StatelessWidget {
child: InkWell(
borderRadius: BorderRadius.circular(AppConfig.borderRadius),
onTap: onTap,
onLongPress: onLongPress,
child: Container(
height: maxWidth,
width: maxWidth,

View file

@ -192,6 +192,31 @@ class VocabAnalyticsListView extends StatelessWidget {
),
],
)
: controller.selectMode
? Row(
mainAxisAlignment: .spaceBetween,
key: const ValueKey('selection'),
children: [
Row(
mainAxisSize: .min,
children: [
IconButton(
onPressed: controller.clearSelectedConstructs,
icon: const Icon(Icons.close),
),
Text(
"${controller.selectedConstructs.length}",
style: Theme.of(context).textTheme.bodyLarge,
),
],
),
IconButton(
onPressed: controller.blockSelectedConstructs,
icon: Icon(Icons.delete_outline),
color: Theme.of(context).colorScheme.error,
),
],
)
: Row(
spacing: FluffyThemes.isColumnMode(context) ? 16.0 : 4.0,
mainAxisAlignment: MainAxisAlignment.end,
@ -245,20 +270,27 @@ class VocabAnalyticsListView extends StatelessWidget {
delegate: SliverChildBuilderDelegate((context, index) {
final vocabItem = filteredVocab[index];
return VocabAnalyticsListTile(
onTap: () {
TtsController.tryToSpeak(
vocabItem.id.lemma,
langCode: MatrixState
.pangeaController
.userController
.userL2Code!,
pos: vocabItem.id.category,
);
AnalyticsNavigationUtil.navigateToAnalytics(
context: context,
view: ProgressIndicatorEnum.wordsUsed,
construct: vocabItem.id,
);
onTap: controller.selectMode
? () => controller.toggleSelectedConstruct(
vocabItem.id,
)
: () {
TtsController.tryToSpeak(
vocabItem.id.lemma,
langCode: MatrixState
.pangeaController
.userController
.userL2Code!,
pos: vocabItem.id.category,
);
AnalyticsNavigationUtil.navigateToAnalytics(
context: context,
view: ProgressIndicatorEnum.wordsUsed,
construct: vocabItem.id,
);
},
onLongPress: () {
controller.toggleSelectedConstruct(vocabItem.id);
},
constructId: vocabItem.id,
textColor:
@ -266,7 +298,11 @@ class VocabAnalyticsListView extends StatelessWidget {
? vocabItem.lemmaCategory.darkColor(context)
: vocabItem.lemmaCategory.color(context),
level: vocabItem.lemmaCategory,
selected: vocabItem.id == selectedConstruct,
selected:
vocabItem.id == selectedConstruct ||
controller.selectedConstructs.contains(
vocabItem.id,
),
);
}, childCount: filteredVocab.length),
),