-
Notifications
You must be signed in to change notification settings - Fork 1
/
metadate.lua
179 lines (151 loc) · 4.29 KB
/
metadate.lua
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
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
--[[
documentation: change modification time of pictures/videos
usage: lua metadate.lua <dir>
usage: lua metadate.lua /media/laz/lg/snimki/2018___pixel2/E/
usage: lua metadate.lua /home/laz/Pictures/
dependencies: https://keplerproject.github.io/luafilesystem/
]]
local lfs = require "lfs"
local function doCommand (command)
local f = assert(io.popen(command, "r"))
local content = f:read("*all")
f:close()
return content or ""
end
-- format: IMG_20190130_112233_1.jpg
local function isMedia (fileName)
local words = {}
for word in fileName:gmatch("%w+") do
words[#words+1]=word
end
if -- media
(#words == 4 or #words == 5) and
words[2]:len() == 8 and
words[3]:len() == 6 and
(
words[#words]:lower() == "jpg" or
words[#words]:lower() == "png" or
words[#words]:lower() == "mp4"
)
or -- media folder
(#words == 3 and
words[2]:len() == 8 and
words[3]:len() == 6
)
then
local media ={}
media.year = words[2]:sub(1,4)
media.month = words[2]:sub(5,6)
media.date = words[2]:sub(7,8)
media.hour = words[3]:sub(1,2)
media.minute = words[3]:sub(3,4)
media.second = words[3]:sub(5,6)
return media
end -- check
end -- isMedia
local function processMedia (fileName, fileNamePath)
local media = isMedia(fileName)
if media then
--print("# media: " .. fileNamePath)
local fileDate = string.format("%s:%s:%s %s:%s:%s",
media.year, media.month, media.date,
media.hour, media.minute, media.second)
--if not doCommand("exiv2 " .. fileNamePath):find("Image timestamp : " .. fileDate, 1, true) then
if not doCommand("exiftool " .. fileNamePath):find("Create Date : " .. fileDate, 1, true) then
print("# update : " .. fileNamePath)
print(doCommand(string.format("exiftool -AllDates='%s' -overwrite_original %s", fileDate, fileNamePath)))
end
else
print("# no media: " .. fileNamePath)
end
end
local function fileContent (fileName)
local file, err = io.open(fileName, "r")
if file == nil then
print("# error: " .. fileName)
print(err)
return ""
end
local content = file:read("*all")
file:close()
return content
end
local function processMediaFolder (fromObject, paths)
for i=1,#paths do
local fileName = paths[i].name
local fileNamePath = paths[i].path
local attrFrom, errFrom = lfs.attributes(fileNamePath)
if attrFrom and attrFrom.mode == "file" then
-- new file name
local words = {}
for word in fileName:gmatch("%w+") do
words[#words+1]=word
end
local newFileName = fromObject.name .. "_" .. i .. "." .. words[#words]
local newFileNamePath = fromObject.path .. "_" .. i .. "." .. words[#words]
print("# create: " .. newFileNamePath)
-- copy file to new destination
local file, err = io.open(newFileNamePath, "w")
if file == nil then
print("# error: " .. newFileNamePath)
print(err)
end
file:write(fileContent(fileNamePath))
file:close()
-- fix metadata
--processMedia(newFileName, newFileNamePath)
end
end
end
local counter = 0
local traverse
traverse = function (file, func)
local from, fromObject
if not file then
return
elseif type(file) == "string" then
from = file
elseif type(file) == "table" then
from = file.path
fromObject = file
end
local attrFrom, errFrom = lfs.attributes(from)
if not attrFrom then return end
if attrFrom.mode == "directory" then
print("# traverse: " .. from)
local paths = {}
for entry in lfs.dir(from) do
if entry ~= "." and entry ~= ".." then
local pathFrom
if from ~= "/" then
if from:sub(#from,#from) == "/" then
pathFrom = from .. entry
else
pathFrom = from .. "/" .. entry
end
else
pathFrom = "/" .. entry
end
paths[#paths+1] = {path = pathFrom, name = entry}
end
end
if #paths > 0 then
table.sort(paths, function(x,y) return x.path < y.path end)
if fromObject and isMedia(fromObject.name, fromObject.path) then
processMediaFolder(fromObject, paths)
else
for i=1,#paths do traverse(paths[i], func) end
end
end
elseif attrFrom.mode == "file" then
counter = counter + 1
--print("# traverse: [" .. counter .. "] " .. from)
if fromObject and func then func(fromObject.name, fromObject.path) end
end
end
if #arg < 1 then
print("usage: lua metadate.lua <dir>")
return
end
traverse(arg[1], processMedia)
print("### end ###\n")