@@ -121,6 +121,7 @@ - (NSArray *)filterOpenFiles:(NSArray *)filenames
121121- (void )handleXcodeModEvent : (NSAppleEventDescriptor *)event
122122 replyEvent : (NSAppleEventDescriptor *)reply ;
123123#endif
124+ + (NSDictionary *)parseOpenURL : (NSURL *)url ;
124125- (void )handleGetURLEvent : (NSAppleEventDescriptor *)event
125126 replyEvent : (NSAppleEventDescriptor *)reply ;
126127- (NSMutableDictionary *)extractArgumentsFromOdocEvent :
@@ -523,30 +524,7 @@ - (void)applicationDidFinishLaunching:(NSNotification *)notification
523524 // If the current version is larger, set that to be stored. Don't
524525 // want to do it otherwise to prevent testing older versions flipping
525526 // the stored version back to an old one.
526- NSArray <NSString *> *lastUsedVersionItems = [lastUsedVersion componentsSeparatedByString: @" ." ];
527- NSArray <NSString *> *currentVersionItems = [currentVersion componentsSeparatedByString: @" ." ];
528- // Compare two arrays lexographically. We just assume that version
529- // numbers are also X.Y.Z… with no "beta" etc texts.
530- BOOL currentVersionLarger = NO ;
531- for (int i = 0 ; i < currentVersionItems.count || i < lastUsedVersionItems.count ; i++) {
532- if (i >= currentVersionItems.count ) {
533- currentVersionLarger = NO ;
534- break ;
535- }
536- if (i >= lastUsedVersionItems.count ) {
537- currentVersionLarger = YES ;
538- break ;
539- }
540- if (currentVersionItems[i].integerValue > lastUsedVersionItems[i].integerValue ) {
541- currentVersionLarger = YES ;
542- break ;
543- }
544- else if (currentVersionItems[i].integerValue < lastUsedVersionItems[i].integerValue ) {
545- currentVersionLarger = NO ;
546- break ;
547- }
548- }
549-
527+ const BOOL currentVersionLarger = (compareSemanticVersions (lastUsedVersion, currentVersion) == 1 );
550528 if (currentVersionLarger) {
551529 [ud setValue: currentVersion forKey: MMLastUsedBundleVersionKey];
552530
@@ -2130,6 +2108,73 @@ - (void)handleXcodeModEvent:(NSAppleEventDescriptor *)event
21302108}
21312109#endif
21322110
2111+ + (NSDictionary *)parseOpenURL : (NSURL *)url
2112+ {
2113+ NSMutableDictionary *dict = [NSMutableDictionary dictionary ];
2114+
2115+ // Parse query ("url=file://...&line=14") into a dictionary
2116+ NSArray *queries = [[url query ] componentsSeparatedByString: @" &" ];
2117+ NSEnumerator *enumerator = [queries objectEnumerator ];
2118+ NSString *param;
2119+ while ((param = [enumerator nextObject ])) {
2120+ // query: <field>=<value>
2121+ NSArray *arr = [param componentsSeparatedByString: @" =" ];
2122+ if ([arr count ] == 2 ) {
2123+ // parse field
2124+ NSString *f = [arr objectAtIndex: 0 ];
2125+ #if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_11
2126+ f = [f stringByRemovingPercentEncoding ];
2127+ #else
2128+ f = [f stringByReplacingPercentEscapesUsingEncoding: NSUTF8StringEncoding];
2129+ #endif
2130+
2131+ // parse value
2132+ NSString *v = [arr objectAtIndex: 1 ];
2133+
2134+ // We need to decode the parameters here because most URL
2135+ // parsers treat the query component as needing to be decoded
2136+ // instead of treating it as is. It does mean that a link to
2137+ // open file "/tmp/file name.txt" will be
2138+ // mvim://open?url=file:///tmp/file%2520name.txt to encode a
2139+ // URL of file:///tmp/file%20name.txt. This double-encoding is
2140+ // intentional to follow the URL spec.
2141+ #if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_11
2142+ v = [v stringByRemovingPercentEncoding ];
2143+ #else
2144+ v = [v stringByReplacingPercentEscapesUsingEncoding: NSUTF8StringEncoding];
2145+ #endif
2146+
2147+ if ([f isEqualToString: @" url" ]) {
2148+ // Since the URL scheme uses a double-encoding due to a
2149+ // file:// URL encoded in another mvim: one, existing tools
2150+ // like iTerm2 could sometimes erroneously only do a single
2151+ // encode. To maximize compatiblity, we re-encode invalid
2152+ // characters if we detect them as they would not work
2153+ // later on when we pass this string to URLWithString.
2154+ //
2155+ // E.g. mvim://open?uri=file:///foo%20bar => "file:///foo bar"
2156+ // which is not a valid URL, so we re-encode it to
2157+ // file:///foo%20bar here. The only important case is to
2158+ // not touch the "%" character as it introduces ambiguity
2159+ // and the re-encoding is a nice compatibility feature, but
2160+ // the canonical form should be double-encoded, i.e.
2161+ // mvim://open?uri=file:///foo%2520bar
2162+ #if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_10
2163+ if (AVAILABLE_MAC_OS (10 , 10 )) {
2164+ NSMutableCharacterSet *charSet = [NSMutableCharacterSet characterSetWithCharactersInString: @" %" ];
2165+ [charSet formUnionWithCharacterSet: NSCharacterSet .URLHostAllowedCharacterSet];
2166+ [charSet formUnionWithCharacterSet: NSCharacterSet .URLPathAllowedCharacterSet];
2167+ v = [v stringByAddingPercentEncodingWithAllowedCharacters: charSet];
2168+ }
2169+ #endif
2170+ }
2171+
2172+ [dict setValue: v forKey: f];
2173+ }
2174+ }
2175+ return dict;
2176+ }
2177+
21332178- (void )handleGetURLEvent : (NSAppleEventDescriptor *)event
21342179 replyEvent : (NSAppleEventDescriptor *)reply
21352180{
@@ -2138,7 +2183,7 @@ - (void)handleGetURLEvent:(NSAppleEventDescriptor *)event
21382183 stringValue ]];
21392184
21402185 // We try to be compatible with TextMate's URL scheme here, as documented
2141- // at http ://blog. macromates.com/2007/the-textmate-url-scheme/ . Currently,
2186+ // at https ://macromates.com/blog /2007/the-textmate-url-scheme/ . Currently,
21422187 // this means that:
21432188 //
21442189 // The format is: mvim://open?<arguments> where arguments can be:
@@ -2151,66 +2196,8 @@ - (void)handleGetURLEvent:(NSAppleEventDescriptor *)event
21512196 // Example: mvim://open?url=file:///etc/profile&line=20
21522197
21532198 if ([[url host ] isEqualToString: @" open" ]) {
2154- NSMutableDictionary *dict = [NSMutableDictionary dictionary ];
2155-
2156- // Parse query ("url=file://...&line=14") into a dictionary
2157- NSArray *queries = [[url query ] componentsSeparatedByString: @" &" ];
2158- NSEnumerator *enumerator = [queries objectEnumerator ];
2159- NSString *param;
2160- while ((param = [enumerator nextObject ])) {
2161- // query: <field>=<value>
2162- NSArray *arr = [param componentsSeparatedByString: @" =" ];
2163- if ([arr count ] == 2 ) {
2164- // parse field
2165- NSString *f = [arr objectAtIndex: 0 ];
2166- #if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_11
2167- f = [f stringByRemovingPercentEncoding ];
2168- #else
2169- f = [f stringByReplacingPercentEscapesUsingEncoding: NSUTF8StringEncoding];
2170- #endif
2171-
2172- // parse value
2173- NSString *v = [arr objectAtIndex: 1 ];
2174-
2175- // We need to decode the parameters here because most URL
2176- // parsers treat the query component as needing to be decoded
2177- // instead of treating it as is. It does mean that a link to
2178- // open file "/tmp/file name.txt" will be
2179- // mvim://open?url=file:///tmp/file%2520name.txt to encode a
2180- // URL of file:///tmp/file%20name.txt. This double-encoding is
2181- // intentional to follow the URL spec.
2182- #if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_11
2183- v = [v stringByRemovingPercentEncoding ];
2184- #else
2185- v = [v stringByReplacingPercentEscapesUsingEncoding: NSUTF8StringEncoding];
2186- #endif
2187-
2188- if ([f isEqualToString: @" url" ]) {
2189- // Since the URL scheme uses a double-encoding due to a
2190- // file:// URL encoded in another mvim: one, existing tools
2191- // like iTerm2 could sometimes erroneously only do a single
2192- // encode. To maximize compatiblity, we re-encode invalid
2193- // characters if we detect them as they would not work
2194- // later on when we pass this string to URLWithString.
2195- //
2196- // E.g. mvim://open?uri=file:///foo%20bar => "file:///foo bar"
2197- // which is not a valid URL, so we re-encode it to
2198- // file:///foo%20bar here. The only important case is to
2199- // not touch the "%" character as it introduces ambiguity
2200- // and the re-encoding is a nice compatibility feature, but
2201- // the canonical form should be double-encoded, i.e.
2202- // mvim://open?uri=file:///foo%2520bar
2203- #if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_11
2204- NSMutableCharacterSet *charSet = [NSMutableCharacterSet characterSetWithCharactersInString: @" %" ];
2205- [charSet formUnionWithCharacterSet: NSCharacterSet .URLHostAllowedCharacterSet];
2206- [charSet formUnionWithCharacterSet: NSCharacterSet .URLPathAllowedCharacterSet];
2207- v = [v stringByAddingPercentEncodingWithAllowedCharacters: charSet];
2208- #endif
2209- }
2210-
2211- [dict setValue: v forKey: f];
2212- }
2213- }
2199+ // Parse the URL and process it
2200+ NSDictionary *dict = [MMAppController parseOpenURL: url];
22142201
22152202 // Actually open the file.
22162203 NSString *file = [dict objectForKey: @" url" ];
0 commit comments