157 rand = r |
158 rand = r |
158 randmu.Unlock() |
159 randmu.Unlock() |
159 return strconv.Itoa(int(1e9 + r%1e9))[1:] |
160 return strconv.Itoa(int(1e9 + r%1e9))[1:] |
160 } |
161 } |
161 |
162 |
162 // TempFile creates a new temporary file in the directory dir |
163 // TempFile creates a new temporary file in the directory dir, |
163 // with a name beginning with prefix, opens the file for reading |
164 // opens the file for reading and writing, and returns the resulting *os.File. |
164 // and writing, and returns the resulting *File. |
165 // The filename is generated by taking pattern and adding a random |
|
166 // string to the end. If pattern includes a "*", the random string |
|
167 // replaces the last "*". |
165 // If dir is the empty string, TempFile uses the default directory |
168 // If dir is the empty string, TempFile uses the default directory |
166 // for temporary files (see os.TempDir). |
169 // for temporary files (see os.TempDir). |
167 // Multiple programs calling TempFile simultaneously |
170 // Multiple programs calling TempFile simultaneously |
168 // will not choose the same file. The caller can use f.Name() |
171 // will not choose the same file. The caller can use f.Name() |
169 // to find the pathname of the file. It is the caller's responsibility |
172 // to find the pathname of the file. It is the caller's responsibility |
170 // to remove the file when no longer needed. |
173 // to remove the file when no longer needed. |
171 func (a Afero) TempFile(dir, prefix string) (f File, err error) { |
174 func (a Afero) TempFile(dir, pattern string) (f File, err error) { |
172 return TempFile(a.Fs, dir, prefix) |
175 return TempFile(a.Fs, dir, pattern) |
173 } |
176 } |
174 |
177 |
175 func TempFile(fs Fs, dir, prefix string) (f File, err error) { |
178 func TempFile(fs Fs, dir, pattern string) (f File, err error) { |
176 if dir == "" { |
179 if dir == "" { |
177 dir = os.TempDir() |
180 dir = os.TempDir() |
178 } |
181 } |
179 |
182 |
|
183 var prefix, suffix string |
|
184 if pos := strings.LastIndex(pattern, "*"); pos != -1 { |
|
185 prefix, suffix = pattern[:pos], pattern[pos+1:] |
|
186 } else { |
|
187 prefix = pattern |
|
188 } |
|
189 |
180 nconflict := 0 |
190 nconflict := 0 |
181 for i := 0; i < 10000; i++ { |
191 for i := 0; i < 10000; i++ { |
182 name := filepath.Join(dir, prefix+nextSuffix()) |
192 name := filepath.Join(dir, prefix+nextRandom()+suffix) |
183 f, err = fs.OpenFile(name, os.O_RDWR|os.O_CREATE|os.O_EXCL, 0600) |
193 f, err = fs.OpenFile(name, os.O_RDWR|os.O_CREATE|os.O_EXCL, 0600) |
184 if os.IsExist(err) { |
194 if os.IsExist(err) { |
185 if nconflict++; nconflict > 10 { |
195 if nconflict++; nconflict > 10 { |
186 randmu.Lock() |
196 randmu.Lock() |
187 rand = reseed() |
197 rand = reseed() |