-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathassociation.ml
71 lines (60 loc) · 1.94 KB
/
association.ml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
type t =
{ target : string
; link : string }
external symlink_file_target_link : string -> string -> int = "caml_symlink_wrapper"
external fnmatch : string -> string -> bool = "caml_fnmatch_wrapper"
external strerror : unit -> string = "caml_strerror_wrapper"
let printf = Printf.printf
let rec symlink ?(origin=Filename.current_dir_name) ~ignores ~cwd { target; link } =
let target' =
if Filename.is_relative target
then Filename.concat cwd target
else target
and link' =
if Filename.is_relative link
then Filename.concat cwd link
else link
in
let ignores =
let ignore_file = Filename.concat target' "ignore" in
if Sys.file_exists ignore_file
then (
printf " Reading ignore file %s\n\n" ignore_file;
In_channel.(with_open_bin ignore_file input_lines) @ ignores)
else
ignores
in
if not (Sys.file_exists link) then
begin
printf "> mkdir %s\n" link';
Sys.mkdir link 0o777;
end;
let sym filename =
let target'' = Filename.concat target filename
and link'' = Filename.concat link filename in
if Sys.is_directory target'' then
begin
let assoc = { target = target''
; link = link'' }
in
symlink ~origin:(Filename.concat origin "..") ~ignores ~cwd assoc
end
else (* Normal file *)
let target = (Filename.concat target' filename)
and link_name = link''
in
if List.exists (fun ignore_pattern -> fnmatch ignore_pattern filename) ignores
then
printf " \027[34mIgnoring %s\027[0m\n\n" target
else
begin
printf "> ln -s \"%s\" \"%s\"\n" target link_name;
let code = symlink_file_target_link target link_name in
if code == -1 then
printf " \027[31m%s\027[0m\n\n" (strerror ())
else
printf " \027[32mCreated symlink\027[0m\n\n"
end
in
let files = Sys.readdir target in
Array.iter sym files