@@ -19,7 +19,7 @@ namespace AsyncToSyncCodeRoundtripSynchroniserMonitor
19
19
static class AsyncToSyncConverter
20
20
{
21
21
//TODO config file
22
- public static readonly List < KVP > Replacements = new List < KVP > ( )
22
+ public static readonly List < KVP > CS_Replacements = new List < KVP > ( )
23
23
{
24
24
//NB! VS may put the /*--await--*/ on a separate line therefore need handling for various space types after /*--await--*/
25
25
//TODO!: ensure that await starts at word boundary
@@ -41,15 +41,18 @@ static class AsyncToSyncConverter
41
41
new KVP ( "(async\r " , "(/*--async--*/\r " ) ,
42
42
new KVP ( "(async\n " , "(/*--async--*/\n " ) ,
43
43
44
+ new KVP ( @", Task " , @", /*--Task--*/Action " ) , //method argument type
45
+ new KVP ( @"(Task " , @"(/*--Task--*/Action " ) , //method argument type
46
+ new KVP ( @", Task<T> " , @", /*--Task<T>--*/Func<T> " ) , //method argument type
47
+ new KVP ( @"(Task<T> " , @"(/*--Task<T>--*/Func<T> " ) , //method argument type
44
48
new KVP ( @" Task " , @" /*--Task--*/void " ) , //method return type
45
- new KVP ( @"Task " , @"/*--Task--*/Action " ) , //method argument type
46
- new KVP ( @"Task<T> " , @"/*--Task<T>--*/Func<T> " ) , //method argument type
47
49
48
50
new KVP ( @").Wait();" , @")/*--.Wait()--*/;" ) ,
49
51
//new KVP("Task.Delay", "/*--Task.Delay--*/System.Threading.Thread.Sleep"), //this needs special regex in sync to async direction
50
52
new KVP ( @"Task.FromResult" , @"/*--Task.FromResult--*/" ) ,
51
53
new KVP ( @"Task.WhenAll" , @"/*--Task.WhenAll--*/" ) ,
52
- new KVP ( @" AsyncLock" , @" /*--AsyncLock--*/object" ) ,
54
+ new KVP ( @" AsyncLock " , @" /*--AsyncLock--*/object " ) , //TODO!!! add handling for \t \r \n
55
+ new KVP ( @" AsyncLock(" , @" /*--AsyncLock--*/object(" ) ,
53
56
54
57
new KVP ( @"#define ASYNC" , @"#define NOASYNC" ) ,
55
58
} ;
@@ -59,47 +62,96 @@ static class AsyncToSyncConverter
59
62
//private static readonly string AsyncLockReplaceRegexReplacement = @"$1/*--AsyncLock--*/object";
60
63
61
64
62
- private static readonly Regex TaskDelayReplaceRegex = new Regex ( @"Task[.]Delay" , RegexOptions . Singleline | RegexOptions . Compiled ) ;
63
- private const string TaskDelayReplaceRegexReplacement = @"/*--Task.Delay--*/System.Threading.Thread.Sleep" ;
65
+ private static readonly Regex CS_TaskDelayReplaceRegex = new Regex ( @"Task[.]Delay" , RegexOptions . Singleline | RegexOptions . Compiled ) ;
66
+ private const string CS_TaskDelayReplaceRegexReplacement = @"/*--Task.Delay--*/System.Threading.Thread.Sleep" ;
64
67
65
68
66
- private static readonly Regex TaskReplaceRegex = new Regex ( @"(\s+)(async\s+)?Task<([^(]+)>(\s+)" , RegexOptions . Singleline | RegexOptions . Compiled ) ;
67
- private const string TaskReplaceRegexReplacement = @"$1/*--$2Task<--*/$3/*-->--*/$4" ;
69
+ private static readonly Regex CS_TaskReplaceRegex = new Regex ( @"(\s+)(async\s+)?Task<([^(]+)>(\s+)" , RegexOptions . Singleline | RegexOptions . Compiled ) ;
70
+ private const string CS_TaskReplaceRegexReplacement = @"$1/*--$2Task<--*/$3/*-->--*/$4" ;
68
71
69
72
70
- private static readonly Regex AsyncLockReplaceRegex = new Regex ( @"using([^(]*)[(]await(\s+[^(]+)[.]LockAsync[(][)][)]" , RegexOptions . Singleline | RegexOptions . Compiled ) ;
71
- private const string AsyncLockReplaceRegexReplacement = @"/*--using--*/lock$1(/*--await--*/ $2/*--.Lock A s y n c()--*/)" ;
73
+ private static readonly Regex CS_AsyncLockReplaceRegex = new Regex ( @"using([^(]*)[(]await(\s+[^(]+)[.]LockAsync[(][)][)]" , RegexOptions . Singleline | RegexOptions . Compiled ) ;
74
+ private const string CS_AsyncLockReplaceRegexReplacement = @"/*--using--*/lock$1(/*--await--*/ $2/*--.Lock A s y n c()--*/)" ;
75
+
76
+
77
+ private static readonly Regex CS_FuncTaskReplaceRegex = new Regex ( @"([\s,(]+)Func<Task<([^=)]+)>>" , RegexOptions . Singleline | RegexOptions . Compiled ) ;
78
+ private const string CS_FuncTaskReplaceRegexReplacement = @"$1Func</*--Task<--*/$2/*-->--*/>" ;
79
+
80
+
81
+
82
+
83
+ public static readonly List < KVP > PY_Replacements = new List < KVP > ( )
84
+ {
85
+ //TODO!: ensure that matches start at word boundary
86
+
87
+ new KVP ( @"ASYNC = True" , @"ASYNC = False" ) ,
88
+ new KVP ( @"NOASYNC = False" , @"NOASYNC = True" ) ,
89
+
90
+ new KVP ( " aiofiles.open" , " open" ) ,
91
+ new KVP ( "\t aiofiles.open" , "\t open" ) ,
92
+ new KVP ( "\r aiofiles.open" , "\r open" ) ,
93
+ new KVP ( "\n aiofiles.open" , "\n open" ) ,
94
+
95
+ new KVP ( " open" , " io.open" ) ,
96
+ new KVP ( "\t open" , "\t io.open" ) ,
97
+ new KVP ( "\r open" , "\r io.open" ) ,
98
+ new KVP ( "\n open" , "\n io.open" ) ,
99
+ } ;
100
+
101
+
102
+ private static readonly Regex PY_AwaitReplaceRegex = new Regex ( @"(\n\r|\r\n|\n)(\s*)await(\s+)" , RegexOptions . Singleline | RegexOptions . Compiled ) ;
103
+ private const string PY_AwaitReplaceRegexReplacement = @"$1#--$2await$3--$1" ;
104
+
105
+
106
+ private static readonly Regex PY_Await2ReplaceRegex = new Regex ( @"=(\s*)await(\s+)" , RegexOptions . Singleline | RegexOptions . Compiled ) ;
107
+ private const string PY_Await2ReplaceRegexReplacement = @"=#--$1await$2--$1" ;
108
+
109
+
110
+ private static readonly Regex PY_AsyncReplaceRegex = new Regex ( @"(\n\r|\r\n|\n)(\s*)async(\s+)" , RegexOptions . Singleline | RegexOptions . Compiled ) ;
111
+ private const string PY_AsyncRegexReplacement = @"$1#--$2async$3--$2" ;
72
112
73
113
74
- private static readonly Regex FuncTaskReplaceRegex = new Regex ( @"([\s,(]+)Func<Task<([^=)]+)>>" , RegexOptions . Singleline | RegexOptions . Compiled ) ;
75
- private const string FuncTaskReplaceRegexReplacement = @"$1Func</*--Task<--*/$2/*-->--*/>" ;
76
114
77
115
78
116
public static async Task AsyncFileUpdated ( string fullName , Context context )
79
117
{
80
118
//using (await Global.FileOperationAsyncLock.LockAsync())
81
119
{
82
- //@"\\?\" prefix is needed for reading from long paths: https://stackoverflow.com/questions/44888844/directorynotfoundexception-when-using-long-paths-in-net-4-7
83
- var fileData = await FileExtensions . ReadAllTextAsync ( @"\\?\" + fullName , context . Token ) ;
120
+ var fileData = await FileExtensions . ReadAllTextAsync ( Extensions . GetLongPath ( fullName ) , context . Token ) ;
84
121
var originalData = fileData ;
85
122
86
123
124
+ if ( fullName . EndsWith ( ".cs" ) )
125
+ {
126
+ foreach ( var replacement in CS_Replacements )
127
+ {
128
+ fileData = fileData . Replace ( replacement . Item1 , replacement . Item2 ) ;
129
+ }
130
+
131
+ fileData = CS_FuncTaskReplaceRegex . Replace ( fileData , CS_FuncTaskReplaceRegexReplacement ) ;
132
+ fileData = CS_AsyncLockReplaceRegex . Replace ( fileData , CS_AsyncLockReplaceRegexReplacement ) ;
133
+ fileData = CS_TaskReplaceRegex . Replace ( fileData , CS_TaskReplaceRegexReplacement ) ;
134
+ fileData = CS_TaskDelayReplaceRegex . Replace ( fileData , CS_TaskDelayReplaceRegexReplacement ) ;
135
+ }
136
+ else if ( fullName . EndsWith ( ".py" ) )
137
+ {
138
+ foreach ( var replacement in PY_Replacements )
139
+ {
140
+ fileData = fileData . Replace ( replacement . Item1 , replacement . Item2 ) ;
141
+ }
87
142
88
- fileData = FuncTaskReplaceRegex . Replace ( fileData , FuncTaskReplaceRegexReplacement ) ;
89
- fileData = AsyncLockReplaceRegex . Replace ( fileData , AsyncLockReplaceRegexReplacement ) ;
90
- fileData = TaskReplaceRegex . Replace ( fileData , TaskReplaceRegexReplacement ) ;
91
- fileData = TaskDelayReplaceRegex . Replace ( fileData , TaskDelayReplaceRegexReplacement ) ;
92
-
93
-
94
- foreach ( var replacement in Replacements )
143
+ fileData = PY_AwaitReplaceRegex . Replace ( fileData , PY_AwaitReplaceRegexReplacement ) ;
144
+ fileData = PY_AsyncReplaceRegex . Replace ( fileData , PY_AsyncRegexReplacement ) ;
145
+ }
146
+ else
95
147
{
96
- fileData = fileData . Replace ( replacement . Item1 , replacement . Item2 ) ;
148
+ throw new NotImplementedException ( "Unknown file extension" ) ;
97
149
}
98
150
99
151
100
152
await ConsoleWatch . SaveFileModifications ( fullName , fileData , originalData , context ) ;
101
153
102
154
} //using (await Global.FileOperationAsyncLock.LockAsync())
103
- }
155
+ } //public static async Task AsyncFileUpdated(string fullName, Context context)
104
156
}
105
157
}
0 commit comments