fakefs 0.18.0 → 0.18.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 9479bf3a7bc17238053ebfe0489449a54eaf93975c253873caa817cb608a6e12
4
- data.tar.gz: e0071c3db4a4b16278a995b0f1ecce76a6781ce23847ef67194a0edb2f2999e2
3
+ metadata.gz: 1b8f0d4485537e8357f305f9d095421de79719f65ada17d30c21443d8f331649
4
+ data.tar.gz: f2cc6f45b43483d18552d92aa2fcc39e8112bb0a0ed5ce17ed05c8ae92410903
5
5
  SHA512:
6
- metadata.gz: 03be56fc4d1a9f05d410e75f2292cb498c0522f9a40508a28763ec757a5b6bf011be8c1462b52292987ea5f594ed54f04f64e1a4baefac2768c4db318ae5f389
7
- data.tar.gz: 7fdd408a1814b6629271d4de1c9610c77836e9d1d8a3dfec8c7c4667bfa4d5fd02e5ed5b85aa111de3e5d5a84808c97b8ced730d2c4cbbad995cb87b703b3014
6
+ metadata.gz: 4fadd520bccc2df062eec7b09324c2d80e3df433d74a969b965dc362e2e7b853ee4f5975688b8eceb325ed4170b580583bebfa34a43e3a8a7d77ca7376f4cc52
7
+ data.tar.gz: 7646dfab7046723fae643785d606ef9a2ab366231780aa63d4e6bce2a20c38688332688f4890573a51df5641dbeade4c6f5a73da38aac9571e9d9b2df92a500e
data/lib/fakefs/file.rb CHANGED
@@ -283,15 +283,16 @@ module FakeFS
283
283
  RealFile.split(path)
284
284
  end
285
285
 
286
- def self.chmod(mode, filename)
286
+ def self.chmod(new_mode, filename)
287
287
  # chmod's mode can either be passed in in absolute mode, or symbolic mode
288
288
  # for reference: https://ruby-doc.org/stdlib-2.2.2/libdoc/fileutils/rdoc/FileUtils.html#method-c-chmod
289
289
  # if the mode is passed in symbolic mode we must convert it to absolute mode
290
- is_absolute_mode = mode.is_a? Numeric
290
+ is_absolute_mode = new_mode.is_a? Numeric
291
291
  unless is_absolute_mode
292
- mode = convert_symbolic_chmod_to_absolute mode
292
+ current_mode = FileSystem.find(filename).mode
293
+ new_mode = convert_symbolic_chmod_to_absolute(new_mode, current_mode)
293
294
  end
294
- FileSystem.find(filename).mode = 0o100000 + mode
295
+ FileSystem.find(filename).mode = 0o100000 + new_mode
295
296
  end
296
297
 
297
298
  # Not exactly right, returns true if the file is chmod +x for owner. In the
@@ -576,15 +577,16 @@ module FakeFS
576
577
  self.class.mtime(@path)
577
578
  end
578
579
 
579
- def chmod(mode)
580
+ def chmod(new_mode)
580
581
  # chmod's mode can either be passed in in absolute mode, or symbolic mode
581
582
  # for reference: https://ruby-doc.org/stdlib-2.2.2/libdoc/fileutils/rdoc/FileUtils.html#method-c-chmod
582
583
  # if the mode is passed in symbolic mode we must convert it to absolute mode
583
- is_absolute_mode = mode.is_a? Numeric
584
+ is_absolute_mode = new_mode.is_a? Numeric
584
585
  unless is_absolute_mode
585
- mode = convert_symbolic_chmod_to_absolute mode
586
+ current_mode = @file.mode
587
+ new_mode = convert_symbolic_chmod_to_absolute(new_mode, current_mode)
586
588
  end
587
- @file.mode = 0o100000 + mode
589
+ @file.mode = 0o100000 + new_mode
588
590
  end
589
591
 
590
592
  def chown(owner_int, group_int)
@@ -688,10 +690,10 @@ module FakeFS
688
690
  read_buf
689
691
  end
690
692
 
691
- def self.convert_symbolic_chmod_to_absolute(mode)
693
+ def self.convert_symbolic_chmod_to_absolute(new_mode, current_mode)
692
694
  # mode always must be of form <GROUP1>=<FLAGS>,<GROUP2>=<FLAGS,...
693
695
  # e.g.: u=wr,go=x
694
- chmod_pairs = mode.split(',')
696
+ chmod_pairs = new_mode.split(',')
695
697
 
696
698
  # - duplicating groups is OK ( e.g.: 'ugouuoouu' is valid and is interpretted as 'ugo' )
697
699
  # - duplicating modes is OK ( e.g.: 'wwwwwwwww' is interpreted as 'w' )
@@ -707,38 +709,56 @@ module FakeFS
707
709
  # or else an error is raised
708
710
  # - in the example above, the following error is raised: 'invalid `who' symbol in file mode: z (ArgumentError)'
709
711
  valid_groups_to_numeric_vals = { 'u' => 0o100, 'g' => 0o10, 'o' => 0o1 }
712
+
713
+ # make sure we preload the current group values.
714
+ # chmod works by calculating new permissions based off of existing permissions
710
715
  current_groups_to_vals = { 0o100 => 0o0, 0o10 => 0o0, 0o1 => 0o0 }
711
- valid_modes_to_numeric_vals = { 'r' => 0o4, 'w' => 0o2, 'x' => 0o1 }
716
+ [0o100, 0o10, 0o1].each do |group_num|
717
+ perm_amt = get_perms_for_group(current_mode, group_num)
718
+ current_groups_to_vals[group_num] = perm_amt
719
+ end
720
+
712
721
  chmod_pairs.each do |pair|
713
- groups = pair.rpartition('=').first
714
- modes = pair.rpartition('=').last
715
-
716
- # if we give no modes, then we are removing all permission
717
- chmod_perm_num = 0o0
718
- if modes != ''
719
- # make sure there are no invalid flags in the modes
720
- # and that we discard duplicates as chmod does
721
- given_modes = modes.split('')
722
- given_modes = given_modes.uniq
723
- given_modes.each do |specific_mode|
724
- # ensure that the mode is valid
725
- unless valid_modes_to_numeric_vals.key? specific_mode
726
- raise ArgumentError, "Invalid `perm' symbol in file mode: #{specific_mode}"
727
- end
722
+ # see if we are dealing with +/- ( granting or removing permissions ) or = ( assigning permissions )
723
+ # note that it IS valid to mix assignment and granting/revoking perissions ( things like u=wrx,g+x are valid )
724
+ assign_perms = '='
725
+ remove_perms = '-'
726
+ add_perms = '+'
727
+ assignment_mode = nil
728
+ if pair.include? remove_perms
729
+ assignment_mode = remove_perms
730
+ elsif pair.include? add_perms
731
+ assignment_mode = add_perms
732
+ elsif pair.include? assign_perms
733
+ assignment_mode = assign_perms
734
+ end
728
735
 
729
- chmod_addend = valid_modes_to_numeric_vals[specific_mode]
730
- chmod_perm_num += chmod_addend
731
- end
736
+ # if we can't find a mode, then raise an exception as real `chmod` would
737
+ if assignment_mode.nil?
738
+ raise ArgumentError, "Invalid file mode: #{mode}"
732
739
  end
740
+ adding_removing_perms = [add_perms, remove_perms].include?(assignment_mode)
741
+
742
+ groups = pair.rpartition(assignment_mode).first
743
+ modes = pair.rpartition(assignment_mode).last
744
+
745
+ # get the numeric chmod value associated with the symbolic entry
746
+ chmod_perm_num = calculate_chmod_amt_for_mode modes
733
747
 
734
748
  # if we give no groups, then we are giving all groups
735
749
  if groups == ''
736
- current_groups_to_vals[0o100] = chmod_perm_num
737
- current_groups_to_vals[0o10] = chmod_perm_num
738
- current_groups_to_vals[0o1] = chmod_perm_num
750
+ if adding_removing_perms
751
+ [0o100, 0o10, 0o1].each do |group_num|
752
+ perm_amt = set_perms_for_group(current_groups_to_vals, group_num, assignment_mode, chmod_perm_num)
753
+ current_groups_to_vals[group_num] = perm_amt
754
+ end
755
+ else
756
+ [0o100, 0o10, 0o1].each do |group_num|
757
+ current_groups_to_vals[group_num] = chmod_perm_num
758
+ end
759
+ end
739
760
  else
740
- # make sure there are no invalid flags in the groups
741
- # and that we discard duplicates as chmod does
761
+ # make sure there are no invalid flags in the groups and that we discard duplicates as chmod does
742
762
  given_groups = groups.split('')
743
763
  given_groups = given_groups.uniq
744
764
  given_groups.each do |specific_group|
@@ -747,9 +767,15 @@ module FakeFS
747
767
  raise ArgumentError, "Invalid `who' symbol in file mode: #{specific_group}"
748
768
  end
749
769
 
750
- # take the current chmod amt from earlier and assosciate that as the current chmod factor for the group
770
+ # take the current chmod amt from earlier and associate that as the current chmod factor for the group
771
+ # if we are adding or removing groups ( via +/- ) then we must make sure that we adjust
772
+ # the current chmod perm number for the group
751
773
  group_num = valid_groups_to_numeric_vals[specific_group]
752
- current_groups_to_vals[group_num] = chmod_perm_num
774
+ adjusted_chmod = chmod_perm_num
775
+ if adding_removing_perms
776
+ adjusted_chmod = set_perms_for_group(current_groups_to_vals, group_num, assignment_mode, chmod_perm_num)
777
+ end
778
+ current_groups_to_vals[group_num] = adjusted_chmod
753
779
  end
754
780
  end
755
781
  end
@@ -758,7 +784,64 @@ module FakeFS
758
784
  0o100 * current_groups_to_vals[0o100] + 0o10 * current_groups_to_vals[0o10] + current_groups_to_vals[0o1]
759
785
  end
760
786
 
761
- private_class_method :convert_symbolic_chmod_to_absolute
787
+ # return the group mode for group num based off the provided current_file_mode
788
+ def self.get_perms_for_group(current_file_mode, group_num)
789
+ # get the current recorded mode of the group and return it to the caller
790
+ # note we don't shift for 'o' since that is the bottom 3 bits
791
+ # note we multiply by 7 since the group num is 1, and octal represents digits 1-7 and we want all 3 bits
792
+ current_group_mode = current_file_mode & (group_num * 7)
793
+ if group_num == 0o100
794
+ current_group_mode = current_group_mode >> 6
795
+ elsif group_num == 0o10
796
+ current_group_mode = current_group_mode >> 3
797
+ end
798
+
799
+ current_group_mode
800
+ end
801
+
802
+ # given the current chmod values for a file return the result of adding or removing chmod_perm_num from the
803
+ # requested groups permissions ( so performing <GROUP>+<PERMS> or <GROUP>-<PERMS>
804
+ def self.set_perms_for_group(current_groups_to_vals, group_num, assignment_mode, chmod_perm_num)
805
+ # get the current recorded mode of the group
806
+ current_group_mode = current_groups_to_vals[group_num]
807
+
808
+ # now that we have the current value of the group, add or remove bits accordingly
809
+ if assignment_mode == '+'
810
+ current_group_mode | chmod_perm_num
811
+ elsif assignment_mode == '-'
812
+ current_group_mode & ~chmod_perm_num
813
+ else
814
+ raise ArguementError "Unknown assignment mode #{assignment_mode}"
815
+ end
816
+ end
817
+
818
+ # given a list of modes [rwx] (a) ensure all modes are valid and (b) return the numeric value
819
+ # associated with the modes
820
+ def self.calculate_chmod_amt_for_mode(modes)
821
+ valid_modes_to_numeric_vals = { 'r' => 0o4, 'w' => 0o2, 'x' => 0o1 }
822
+
823
+ # if we give no modes, then we are removing all permission
824
+ chmod_perm_num = 0o0
825
+ if modes != ''
826
+ # make sure there are no invalid flags in the modes and that we discard duplicates as chmod does
827
+ given_modes = modes.split('')
828
+ given_modes = given_modes.uniq
829
+ given_modes.each do |specific_mode|
830
+ # ensure that the mode is valid
831
+ unless valid_modes_to_numeric_vals.key? specific_mode
832
+ raise ArgumentError, "Invalid `perm' symbol in file mode: #{specific_mode}"
833
+ end
834
+
835
+ chmod_perm_num += valid_modes_to_numeric_vals[specific_mode]
836
+ end
837
+ end
838
+
839
+ chmod_perm_num
840
+ end
841
+
842
+ # split the private class method decleration so rubocop doesn't complain the line is too long
843
+ private_class_method :convert_symbolic_chmod_to_absolute, :calculate_chmod_amt_for_mode
844
+ private_class_method :get_perms_for_group, :set_perms_for_group
762
845
 
763
846
  private
764
847
 
@@ -876,9 +876,9 @@ module FakeFS
876
876
  FileTest.setgid?(@path)
877
877
  end
878
878
 
879
- # See <tt>FileTest.size</tt>.
879
+ # See <tt>FileTest.size?</tt>.
880
880
  def size
881
- FileTest.size(@path)
881
+ FileTest.size?(@path)
882
882
  end
883
883
 
884
884
  # See <tt>FileTest.size?</tt>.
@@ -1,7 +1,7 @@
1
1
  module FakeFS
2
2
  # Version module
3
3
  module Version
4
- VERSION = '0.18.0'.freeze
4
+ VERSION = '0.18.1'.freeze
5
5
 
6
6
  def self.to_s
7
7
  VERSION
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: fakefs
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.18.0
4
+ version: 0.18.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Chris Wanstrath
@@ -12,7 +12,7 @@ authors:
12
12
  autorequire:
13
13
  bindir: bin
14
14
  cert_chain: []
15
- date: 2018-07-23 00:00:00.000000000 Z
15
+ date: 2019-01-16 00:00:00.000000000 Z
16
16
  dependencies:
17
17
  - !ruby/object:Gem::Dependency
18
18
  name: bump
@@ -28,20 +28,6 @@ dependencies:
28
28
  - - "~>"
29
29
  - !ruby/object:Gem::Version
30
30
  version: 0.5.3
31
- - !ruby/object:Gem::Dependency
32
- name: bundler
33
- requirement: !ruby/object:Gem::Requirement
34
- requirements:
35
- - - "~>"
36
- - !ruby/object:Gem::Version
37
- version: '1.3'
38
- type: :development
39
- prerelease: false
40
- version_requirements: !ruby/object:Gem::Requirement
41
- requirements:
42
- - - "~>"
43
- - !ruby/object:Gem::Version
44
- version: '1.3'
45
31
  - !ruby/object:Gem::Dependency
46
32
  name: minitest
47
33
  requirement: !ruby/object:Gem::Requirement