View difference between Paste ID: 2bqr4VVa and Ap6pE2BL
SHOW: | | - or go back to the newest paste.
1-
rednet.open "top"
1+
local f = fs.open("conf", "r")
2
local conf = textutils.unserialise(f.readAll())
3
f.close()
4
5
rednet.open(conf.modem)
6
7
local inventories = {}
8
for _, n in pairs(peripheral.getNames()) do
9
    local p = peripheral.wrap(n)
10
    if 
11
        string.find(n, "chest") or
12
        string.find(n, "shulker") then
13
        inventories[n] = p
14
    end
15
end
16
17
local nameCache = {}
18
19
function cache(item, chest, slot)
20
    local idx = item.name .. ":" .. item.damage
21-
        nameCache[idx] = chest.getItemMeta(slot).displayName
21+
22
    if nameCache[idx] then
23
        return nameCache[idx]
24
    else
25
		local n = chest.getItemMeta(slot).displayName
26
        nameCache[idx] = n
27
		return n
28
    end
29
end
30
31
local index = {}
32-
        os.queueEvent "dummy"
32+
33-
        os.pullEvent "dummy"
33+
34
    local data = inv.list()
35
    
36
    for slot, item in pairs(data) do
37
        data[slot].displayName = cache(item, inv, slot)
38
    end
39
    
40
    index[name] = data
41-
        for n in pairs(inventories) do
41+
42-
            updateIndexFor(n)
42+
43-
            sleep(0.1)
43+
44
	for n in pairs(inventories) do
45
		updateIndexFor(n)
46
		sleep()
47
	end
48
	print "Indexing complete."
49
end
50
51
function find(predicate)
52
    for name, items in pairs(index) do
53
        for slot, item in pairs(items) do
54
            if predicate(item) then
55
                return name, slot, item
56
            end
57
        end
58
    end
59
end
60
61
function findSpace()
62
    for name, items in pairs(index) do
63
        if #items < inventories[name].size() then
64
            return name
65
        end
66
    end
67
end
68
69-
    if msg.cmd == "find" then
69+
70-
        return {find(function(item)
70+
71
72
    if msg.cmd == "extract" then
73
        local inv, slot, item = find(function(item)
74-
                (not msg.dname or string.find(item.displayName, msg.dname))
74+
75-
        end)}
75+
76-
    elseif msg.cmd == "space" then
76+
77-
        return findSpace()
77+
                (not msg.dname or string.find(item.displayName:lower(), msg.dname:lower()))
78
        end)
79
80
		index[inv][slot] = nil
81
82
		local moved = peripheral.call(conf.bufferOutInternal, "pullItems", inv, slot, msg.qty or 64, 1)
83
84
		if msg.destInv then
85
			moved = peripheral.call(conf.bufferOutExternal, "pushItems", msg.destInv, 1)
86
		end
87
88
		return {moved, item}
89
	elseif msg.cmd == "insert" then
90
		if msg.fromInv and msg.fromSlot then
91-
            print(textutils.serialise(r))
91+
			peripheral.call(conf.bufferInExternal, "pullItems", msg.fromInv, msg.fromSlot, msg.qty or 64, 1)
92
		end
93
94
		local toInv = findSpace()
95
		if not toInv then return "ERROR" end
96
		
97-
parallel.waitForAll(updateIndex, processRequests)
97+
		peripheral.call(conf.bufferInInternal, "pushItems", toInv, 1)
98
99
		updateIndexFor(toInv) -- I don't know a good way to figure out where exactly the items went
100
101
		return "OK"
102
	elseif msg.cmd == "buffers" then
103
		return { conf.bufferInExternal, conf.bufferOutExternal }
104
	elseif msg.cmd == "reindex" then
105
		updateIndex()
106
		return "OK"
107
    elseif msg.cmd == "list" then
108
        return index
109
    elseif msg.cmd == "name" then
110
        msg.meta = msg.meta or 0
111
        return msg.name and msg.meta and nameCache[msg.name .. ":" .. msg.meta]
112
    end
113
end
114
115
function processRequests()
116
    while true do
117
        local id, msg = rednet.receive "mw"
118
        if msg and msg.cmd then
119
            local ok, r = pcall(processRequest, msg)
120
121
			if not ok then r = "ERROR" end
122
			
123
            rednet.send(id, r, "mw")
124
        end
125
    end
126
end
127
128
updateIndex()
129
processRequests()