@@ -215,6 +215,8 @@ def get_module_class(cls, host):
215215 return BSDFile
216216 if host .system_info .type == "darwin" :
217217 return DarwinFile
218+ if host .system_info .type == "windows" :
219+ return WindowsFile
218220 raise NotImplementedError
219221
220222
@@ -330,3 +332,173 @@ class NetBSDFile(BSDFile):
330332 @property
331333 def sha256sum (self ):
332334 return self .check_output ("cksum -a sha256 < %s" , self .path )
335+
336+
337+ class WindowsFile (File ):
338+ @property
339+ def exists (self ):
340+ """Test if file exists
341+
342+ >>> host.file(r"C:/Users").exists
343+ True
344+ >>> host.file(r"C:/nonexistent").exists
345+ False
346+ """
347+
348+ return (
349+ self .check_output (r"powershell -command \"Test-Path '%s'\"" , self .path )
350+ == "True"
351+ )
352+
353+ @property
354+ def is_file (self ):
355+ return (
356+ self .check_output (
357+ r"powershell -command \"(Get-Item '%s') -is [System.IO.FileInfo]\"" ,
358+ self .path ,
359+ )
360+ == "True"
361+ )
362+
363+ @property
364+ def is_directory (self ):
365+ return (
366+ self .check_output (
367+ r"powershell -command \"(Get-Item '%s') -is [System.IO.DirectoryInfo]\"" ,
368+ self .path ,
369+ )
370+ == "True"
371+ )
372+
373+ @property
374+ def is_pipe (self ):
375+ raise NotImplementedError
376+
377+ @property
378+ def is_socket (self ):
379+ raise NotImplementedError
380+
381+ @property
382+ def is_symlink (self ):
383+ return (
384+ self .check_output (
385+ r"powershell -command \"(Get-Item -Path '%s').Attributes -band [System.IO.FileAttributes]::ReparsePoint\"" ,
386+ self .path ,
387+ )
388+ == "True"
389+ )
390+
391+ @property
392+ def linked_to (self ):
393+ """Resolve symlink
394+
395+ >>> host.file("C:/Users/lock").linked_to
396+ 'C:/Program Files/lock'
397+ """
398+ return self .check_output (
399+ r"powershell -command \"(Get-Item -Path '%s' -ReadOnly).FullName\"" ,
400+ self .path ,
401+ )
402+
403+ @property
404+ def user (self ):
405+ raise NotImplementedError
406+
407+ @property
408+ def uid (self ):
409+ raise NotImplementedError
410+
411+ @property
412+ def group (self ):
413+ raise NotImplementedError
414+
415+ @property
416+ def gid (self ):
417+ raise NotImplementedError
418+
419+ @property
420+ def mode (self ):
421+ raise NotImplementedError
422+
423+ def contains (self , pattern ):
424+ """Checks content of file for pattern
425+
426+ This follows the regex syntax.
427+ """
428+ return (
429+ self .run_test (
430+ r"powershell -command \"Select-String -Path '%s' -Pattern '%s'\"" ,
431+ self .path ,
432+ pattern ,
433+ ).stdout
434+ != ""
435+ )
436+
437+ @property
438+ def md5sum (self ):
439+ raise NotImplementedError
440+
441+ @property
442+ def sha256sum (self ):
443+ raise NotImplementedError
444+
445+ def _get_content (self , decode ):
446+ out = self .run_expect ([0 ], r"powershell -command \"cat -- '%s'\"" , self .path )
447+ if decode :
448+ return out .stdout
449+ return out .stdout_bytes
450+
451+ @property
452+ def content (self ):
453+ """Return file content as bytes
454+
455+ >>> host.file("C:/Windows/Temp/foo").content
456+ b'caf\\ xc3\\ xa9'
457+ """
458+ return self ._get_content (False )
459+
460+ @property
461+ def content_string (self ):
462+ """Return file content as string
463+
464+ >>> host.file("C:/Windows/Temp/foo").content_string
465+ 'café'
466+ """
467+ return self ._get_content (True )
468+
469+ @property
470+ def mtime (self ):
471+ """Return time of last modification as datetime.datetime object
472+
473+ >>> host.file("C:/Windows/passwd").mtime
474+ datetime.datetime(2015, 3, 15, 20, 25, 40)
475+ """
476+ date_time_str = self .check_output (
477+ r"powershell -command \"Get-ChildItem -Path '%s' | Select-Object -ExpandProperty LastWriteTime\"" ,
478+ self .path ,
479+ )
480+ return datetime .datetime .strptime (
481+ date_time_str .strip (), "%A, %B %d, %Y %I:%M:%S %p"
482+ )
483+
484+ @property
485+ def size (self ):
486+ """Return size of file in bytes"""
487+ return int (
488+ self .check_output (
489+ r"powershell -command \"Get-Item -Path '%s' | Select-Object -ExpandProperty Length\"" ,
490+ self .path ,
491+ )
492+ )
493+
494+ def listdir (self ):
495+ """Return list of items under the directory
496+
497+ >>> host.file("C:/Windows/Temp").listdir()
498+ ['foo_file', 'bar_dir']
499+ """
500+ out = self .check_output (
501+ r"powershell -command \"Get-ChildItem -Path '%s' | Select-Object -ExpandProperty Name\"" ,
502+ self .path ,
503+ )
504+ return [item .strip () for item in out .strip ().split ("\n " )]
0 commit comments