@@ -120,6 +120,15 @@ pub struct AppSessionConfig {
120120 pub default_mode : String ,
121121}
122122
123+ /// A user-defined quick action for the FlowChat post-coding actions menu.
124+ #[ derive( Debug , Clone , Serialize , Deserialize , PartialEq , Eq ) ]
125+ pub struct AiExperienceQuickAction {
126+ pub id : String ,
127+ pub label : String ,
128+ pub prompt : String ,
129+ pub enabled : bool ,
130+ }
131+
123132/// AI experience configuration.
124133#[ derive( Debug , Clone , Serialize , Deserialize ) ]
125134#[ serde( default ) ]
@@ -139,6 +148,9 @@ pub struct AIExperienceConfig {
139148 pub agent_companion_pet : Option < AgentCompanionPetSelection > ,
140149 /// Whether to enable flashgrep-backed accelerated workspace search.
141150 pub enable_workspace_search : bool ,
151+ /// User-defined quick actions (post-coding menu); persisted for the web UI.
152+ #[ serde( default ) ]
153+ pub quick_actions : Vec < AiExperienceQuickAction > ,
142154}
143155
144156/// User-selected Agent companion pet package.
@@ -1285,6 +1297,7 @@ impl Default for AIExperienceConfig {
12851297 agent_companion_display_mode : "desktop" . to_string ( ) ,
12861298 agent_companion_pet : None ,
12871299 enable_workspace_search : false ,
1300+ quick_actions : Vec :: new ( ) ,
12881301 }
12891302 }
12901303}
@@ -1785,6 +1798,56 @@ mod tests {
17851798 ) ;
17861799 }
17871800
1801+ #[ test]
1802+ fn ai_experience_quick_actions_round_trip_through_global_config ( ) {
1803+ let config: GlobalConfig = serde_json:: from_value ( serde_json:: json!( {
1804+ "app" : {
1805+ "language" : "en-US" ,
1806+ "auto_update" : true ,
1807+ "telemetry" : true ,
1808+ "startup_behavior" : "default" ,
1809+ "confirm_on_exit" : true ,
1810+ "restore_windows" : false ,
1811+ "zoom_level" : 100 ,
1812+ "sidebar" : { "width" : 260 , "collapsed" : false } ,
1813+ "right_panel" : { "width" : 400 , "collapsed" : true } ,
1814+ "notifications" : {
1815+ "enabled" : true ,
1816+ "position" : "top-right" ,
1817+ "duration" : 4000 ,
1818+ "dialog_completion_notify" : true ,
1819+ "enable_startup_tips" : true
1820+ } ,
1821+ "session_config" : { "default_mode" : "code" } ,
1822+ "ai_experience" : {
1823+ "enable_session_title_generation" : true ,
1824+ "enable_welcome_panel_ai_analysis" : false ,
1825+ "enable_visual_mode" : false ,
1826+ "enable_agent_companion" : true ,
1827+ "agent_companion_display_mode" : "desktop" ,
1828+ "enable_workspace_search" : false ,
1829+ "quick_actions" : [
1830+ {
1831+ "id" : "custom_1" ,
1832+ "label" : "Run tests" ,
1833+ "prompt" : "Run the test suite" ,
1834+ "enabled" : true
1835+ }
1836+ ]
1837+ }
1838+ }
1839+ } ) )
1840+ . expect ( "minimal app config with quick_actions should deserialize" ) ;
1841+
1842+ let actions = & config. app . ai_experience . quick_actions ;
1843+ assert_eq ! ( actions. len( ) , 1 ) ;
1844+ assert_eq ! ( actions[ 0 ] . id, "custom_1" ) ;
1845+ assert_eq ! ( actions[ 0 ] . label, "Run tests" ) ;
1846+
1847+ let serialized = serde_json:: to_value ( & config) . expect ( "config should serialize" ) ;
1848+ assert_eq ! ( serialized[ "app" ] [ "ai_experience" ] [ "quick_actions" ] [ 0 ] [ "id" ] , "custom_1" ) ;
1849+ }
1850+
17881851 #[ test]
17891852 fn deserializes_compatibility_false_thinking_flag_into_default_reasoning_mode ( ) {
17901853 let config: AIModelConfig = serde_json:: from_value ( serde_json:: json!( {
0 commit comments