Deprecated: trim(): Passing null to parameter #1 ($string) of type string is deprecated in /var/www/html/extensions/Variables/includes/ExtVariables.php on line 198

Deprecated: trim(): Passing null to parameter #1 ($string) of type string is deprecated in /var/www/html/extensions/Variables/includes/ExtVariables.php on line 198

Deprecated: trim(): Passing null to parameter #1 ($string) of type string is deprecated in /var/www/html/extensions/Variables/includes/ExtVariables.php on line 198
WorkflowKit.framework: Difference between revisions - iPhone Development Wiki

WorkflowKit.framework: Difference between revisions

From iPhone Development Wiki
(Added docs for the WorkflowKit framework)
(No difference)

Revision as of 13:44, 31 March 2022

WorkflowKit.framework
Private Framework
Availabile 12.0 – present
Headers [headers.cynder.me]


WorkflowKit is the framework that acts as a backend to the Shortcuts app. It provides around 80% functionality of the Shortcuts app including (but not limited to) actions (though ActionKit also powers a lot of them), handles how shortcuts are imported, how they're stored, etc. It is noted that while it is technically added in 12.0, most of its functionality came in iOS 13.0.

For examples on how to use this framework, see the Example Code section of this page.

WFWorkflowRecord

WFWorkflowRecord is how shortcuts are stored. The biggest thing is actions: Every action has an action identifier to identify an action (WFWorkflowActionIdentifier), and some have parameters of what is in said action (WFWorkflowActionParameters). However, it also handles other data about the shortcut, such as its name and minimum client version it can be imported on.

Example Code

Replacing Return to Homescreen with Exit Shortcut upon shortcut import

%hook WFSharedShortcut
-(id)workflowRecord {
// WFWorkflowRecord handles how shortcuts are stored and hooking it will affect every shortcut loaded - not only is this bad for performance, but if you make a mistake, every shortcut will be affected, hence it's best to avoid hooking it when possible. Here, we hook WFSharedShortcut and affect its workflow record instead
    id rettype = %orig;
    id rettypeactions = [rettype actions];
    NSArray *origShortcutActions = rettypeactions;
    NSArray *newShortcutActions = rettypeactions;
    NSMutableArray *newMutableShortcutActions = [newShortcutActions mutableCopy];
    int shortcutActionsObjectIndex = 0;
    
    for (id shortcutActionsObject in origShortcutActions) {
        if ([shortcutActionsObject isKindOfClass:[NSDictionary class]]){
            if ([shortcutActionsObject objectForKey:@"WFWorkflowActionIdentifier"]) {
// All shortcuts have an identifier to help identify the action (is.workflow.actions.returntohomescreen is Return to Homescreen, is.workflow.actions.exit is Exit Shortcut). You can find the default action identifiers in /System/​Library/​PrivateFrameworks/​WorkflowKit.framework/WFActions.plist
            if ([[shortcutActionsObject valueForKey:@"WFWorkflowActionIdentifier"] isEqual:@"is.workflow.actions.returntohomescreen"]) {
            NSMutableDictionary *mutableShortcutActionsObject = [shortcutActionsObject mutableCopy];
// While not demo'ed in this example, actions also have WFWorkflowActionParameters. For example, the file path in Get File is the WFGetFilePath parameter. These can also be found in WFActions.plist, or by extracting an unsigned .shortcut/.wflow file and looking to see the parameters of the action in the shortcut.
    
            [mutableShortcutActionsObject setValue:@"is.workflow.actions.exit" forKey:@"WFWorkflowActionIdentifier"];
    
            NSDictionary *newShortDict = [[NSDictionary alloc] initWithDictionary:mutableShortcutActionsObject];
            newMutableShortcutActions[shortcutActionsObjectIndex] = newShortDict;
            }
            }
        }
        shortcutActionsObjectIndex++;
    }
    
    shortcutActionsObjectIndex = 0;

    rettypeactions = [[NSArray alloc] initWithArray:newMutableShortcutActions];
    [rettype setActions:newMutableShortcutActions];
    return rettype;
}
%end

References